Version 0.4.4.0 .

svn merge -r 20419:20669 https://dart.googlecode.com/svn/branches/bleeding_edge trunk

git-svn-id: http://dart.googlecode.com/svn/trunk@20676 260f80e4-7a28-3924-810f-c04153c831b5
diff --git a/.gitignore b/.gitignore
index 293bd10..4da6b24 100644
--- a/.gitignore
+++ b/.gitignore
@@ -55,3 +55,4 @@
 
 # Generated files.
 tools/out
+tools/xcodebuild
diff --git a/compiler/api.dart b/compiler/api.dart
index 95102e7..660dd83 100644
--- a/compiler/api.dart
+++ b/compiler/api.dart
@@ -1,5 +1,5 @@
-#library("api");
+library api;
 // dart:core is implicit
-#import("dart:html");
-#import("dart:json");
-#import("dart:isolate");
+import "dart:html";
+import "dart:json";
+import "dart:isolate";
diff --git a/compiler/tests/dartc/test_config.dart b/compiler/tests/dartc/test_config.dart
index c9b3607..ccda857 100644
--- a/compiler/tests/dartc/test_config.dart
+++ b/compiler/tests/dartc/test_config.dart
@@ -2,9 +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.
 
-#library("junit_dartc_test_config");
+library junit_dartc_test_config;
 
-#import("../../../tools/testing/dart/test_suite.dart");
+import "../../../tools/testing/dart/test_suite.dart";
 
 class JUnitDartcTestSuite extends JUnitTestSuite {
   JUnitDartcTestSuite(Map configuration)
diff --git a/pkg/analyzer_experimental/example/resolver_driver.dart b/pkg/analyzer_experimental/example/resolver_driver.dart
index e1bcd68..d28d964 100644
--- a/pkg/analyzer_experimental/example/resolver_driver.dart
+++ b/pkg/analyzer_experimental/example/resolver_driver.dart
@@ -32,10 +32,10 @@
   ChangeSet changeSet = new ChangeSet();
   changeSet.added(source);
   context.applyChanges(changeSet);
-  LibraryElement libElement = context.getLibraryElement(source);
+  LibraryElement libElement = context.computeLibraryElement(source);
   print("libElement: $libElement");
 
-  CompilationUnit resolvedUnit = context.resolve(source, libElement);
+  CompilationUnit resolvedUnit = context.resolveCompilationUnit(source, libElement);
   var visitor = new _ASTVisitor();
   resolvedUnit.accept(visitor);
 }
@@ -44,7 +44,7 @@
   visitNode(ASTNode node) {
     String text = '${node.runtimeType} : <"${node.toString()}">';
     if (node is SimpleIdentifier) {
-      Element element = node.element;
+      Element element = (node as SimpleIdentifier).element;
       if (element != null) {
         text += " element: ${element.runtimeType}";
         LibraryElement library = element.library;
diff --git a/pkg/analyzer_experimental/lib/src/generated/ast.dart b/pkg/analyzer_experimental/lib/src/generated/ast.dart
index 931fa95..cc22cd4 100644
--- a/pkg/analyzer_experimental/lib/src/generated/ast.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/ast.dart
@@ -284,6 +284,7 @@
   R visitPrefixExpression(PrefixExpression node);
   R visitPropertyAccess(PropertyAccess node);
   R visitRedirectingConstructorInvocation(RedirectingConstructorInvocation node);
+  R visitRethrowExpression(RethrowExpression node);
   R visitReturnStatement(ReturnStatement node);
   R visitScriptTag(ScriptTag node);
   R visitShowCombinator(ShowCombinator node);
@@ -411,12 +412,20 @@
    */
   NodeList<Annotation> get metadata => _metadata;
   /**
-   * Set the documentation comment associated with this node to the given comment
+   * Set the documentation comment associated with this node to the given comment.
    * @param comment the documentation comment to be associated with this node
    */
   void set documentationComment(Comment comment2) {
     this._comment = becomeParentOf(comment2);
   }
+  /**
+   * Set the metadata associated with this node to the given metadata.
+   * @param metadata the metadata to be associated with this node
+   */
+  void set metadata(List<Annotation> metadata2) {
+    this._metadata.clear();
+    this._metadata.addAll(metadata2);
+  }
   void visitChildren(ASTVisitor<Object> visitor) {
     if (commentIsBeforeAnnotations()) {
       safelyVisitChild(_comment, visitor);
@@ -7695,9 +7704,9 @@
    * @return the element representing the parameter being named by this expression
    */
   ParameterElement get element {
-    Element element20 = _name.label.element;
-    if (element20 is ParameterElement) {
-      return element20 as ParameterElement;
+    Element element22 = _name.label.element;
+    if (element22 is ParameterElement) {
+      return element22 as ParameterElement;
     }
     return null;
   }
@@ -8719,6 +8728,49 @@
   }
 }
 /**
+ * Instances of the class {@code RethrowExpression} represent a rethrow expression.
+ * <pre>
+ * rethrowExpression ::=
+ * 'rethrow'
+ * </pre>
+ * @coverage dart.engine.ast
+ */
+class RethrowExpression extends Expression {
+  /**
+   * The token representing the 'rethrow' keyword.
+   */
+  Token _keyword;
+  /**
+   * Initialize a newly created rethrow expression.
+   * @param keyword the token representing the 'rethrow' keyword
+   */
+  RethrowExpression.full(Token keyword) {
+    this._keyword = keyword;
+  }
+  /**
+   * Initialize a newly created rethrow expression.
+   * @param keyword the token representing the 'rethrow' keyword
+   */
+  RethrowExpression({Token keyword}) : this.full(keyword);
+  accept(ASTVisitor visitor) => visitor.visitRethrowExpression(this);
+  Token get beginToken => _keyword;
+  Token get endToken => _keyword;
+  /**
+   * Return the token representing the 'rethrow' keyword.
+   * @return the token representing the 'rethrow' keyword
+   */
+  Token get keyword => _keyword;
+  /**
+   * Set the token representing the 'rethrow' keyword to the given token.
+   * @param keyword the token representing the 'rethrow' keyword
+   */
+  void set keyword(Token keyword15) {
+    this._keyword = keyword15;
+  }
+  void visitChildren(ASTVisitor<Object> visitor) {
+  }
+}
+/**
  * Instances of the class {@code ReturnStatement} represent a return statement.
  * <pre>
  * returnStatement ::=
@@ -8788,8 +8840,8 @@
    * Set the token representing the 'return' keyword to the given token.
    * @param keyword the token representing the 'return' keyword
    */
-  void set keyword(Token keyword15) {
-    this._keyword = keyword15;
+  void set keyword(Token keyword16) {
+    this._keyword = keyword16;
   }
   /**
    * Set the semicolon terminating the statement to the given token.
@@ -8952,8 +9004,8 @@
    * Set the token representing either the 'final', 'const' or 'var' keyword to the given token.
    * @param keyword the token representing either the 'final', 'const' or 'var' keyword
    */
-  void set keyword(Token keyword16) {
-    this._keyword = keyword16;
+  void set keyword(Token keyword17) {
+    this._keyword = keyword17;
   }
   /**
    * Set the name of the declared type of the parameter to the given type name.
@@ -9383,8 +9435,8 @@
    * Set the token for the 'super' keyword to the given token.
    * @param keyword the token for the 'super' keyword
    */
-  void set keyword(Token keyword17) {
-    this._keyword = keyword17;
+  void set keyword(Token keyword18) {
+    this._keyword = keyword18;
   }
   /**
    * Set the token for the period before the name of the constructor that is being invoked to the
@@ -9436,8 +9488,8 @@
    * Set the token representing the keyword to the given token.
    * @param keyword the token representing the keyword
    */
-  void set keyword(Token keyword18) {
-    this._keyword = keyword18;
+  void set keyword(Token keyword19) {
+    this._keyword = keyword19;
   }
   void visitChildren(ASTVisitor<Object> visitor) {
   }
@@ -9615,8 +9667,8 @@
    * Set the token representing the 'case' or 'default' keyword to the given token.
    * @param keyword the token representing the 'case' or 'default' keyword
    */
-  void set keyword(Token keyword19) {
-    this._keyword = keyword19;
+  void set keyword(Token keyword20) {
+    this._keyword = keyword20;
   }
 }
 /**
@@ -9737,8 +9789,8 @@
    * Set the token representing the 'switch' keyword to the given token.
    * @param keyword the token representing the 'switch' keyword
    */
-  void set keyword(Token keyword20) {
-    this._keyword = keyword20;
+  void set keyword(Token keyword21) {
+    this._keyword = keyword21;
   }
   /**
    * Set the left curly bracket to the given token.
@@ -9810,8 +9862,8 @@
    * Set the token representing the keyword to the given token.
    * @param keyword the token representing the keyword
    */
-  void set keyword(Token keyword21) {
-    this._keyword = keyword21;
+  void set keyword(Token keyword22) {
+    this._keyword = keyword22;
   }
   void visitChildren(ASTVisitor<Object> visitor) {
   }
@@ -9820,8 +9872,7 @@
  * Instances of the class {@code ThrowExpression} represent a throw expression.
  * <pre>
  * throwExpression ::=
- * 'throw' {@link Expression expression}? ';'
- * </pre>
+ * 'throw' {@link Expression expression}</pre>
  * @coverage dart.engine.ast
  */
 class ThrowExpression extends Expression {
@@ -9830,9 +9881,7 @@
    */
   Token _keyword;
   /**
-   * The expression computing the exception to be thrown, or {@code null} if the current exception
-   * is to be re-thrown. (The latter case can only occur if the throw statement is inside a catch
-   * clause.)
+   * The expression computing the exception to be thrown.
    */
   Expression _expression;
   /**
@@ -9859,9 +9908,7 @@
     return _keyword;
   }
   /**
-   * Return the expression computing the exception to be thrown, or {@code null} if the current
-   * exception is to be re-thrown. (The latter case can only occur if the throw statement is inside
-   * a catch clause.)
+   * Return the expression computing the exception to be thrown.
    * @return the expression computing the exception to be thrown
    */
   Expression get expression => _expression;
@@ -9881,8 +9928,8 @@
    * Set the token representing the 'throw' keyword to the given token.
    * @param keyword the token representing the 'throw' keyword
    */
-  void set keyword(Token keyword22) {
-    this._keyword = keyword22;
+  void set keyword(Token keyword23) {
+    this._keyword = keyword23;
   }
   void visitChildren(ASTVisitor<Object> visitor) {
     safelyVisitChild(_expression, visitor);
@@ -10143,8 +10190,8 @@
    * Set the token representing the 'typedef' keyword to the given token.
    * @param keyword the token representing the 'typedef' keyword
    */
-  void set keyword(Token keyword23) {
-    this._keyword = keyword23;
+  void set keyword(Token keyword24) {
+    this._keyword = keyword24;
   }
   /**
    * Set the semicolon terminating the declaration to the given token.
@@ -10399,8 +10446,8 @@
    * Set the token representing the 'assert' keyword to the given token.
    * @param keyword the token representing the 'assert' keyword
    */
-  void set keyword(Token keyword24) {
-    this._keyword = keyword24;
+  void set keyword(Token keyword25) {
+    this._keyword = keyword25;
   }
   /**
    * Set the name of the type parameter to the given identifier.
@@ -10716,7 +10763,7 @@
  * | {@link TypeName type}</pre>
  * @coverage dart.engine.ast
  */
-class VariableDeclarationList extends ASTNode {
+class VariableDeclarationList extends AnnotatedNode {
   /**
    * The token representing the 'final', 'const' or 'var' keyword, or {@code null} if no keyword was
    * included.
@@ -10732,11 +10779,13 @@
   NodeList<VariableDeclaration> _variables;
   /**
    * Initialize a newly created variable declaration list.
+   * @param comment the documentation comment associated with this declaration list
+   * @param metadata the annotations associated with this declaration list
    * @param keyword the token representing the 'final', 'const' or 'var' keyword
    * @param type the type of the variables being declared
    * @param variables a list containing the individual variables being declared
    */
-  VariableDeclarationList.full(Token keyword, TypeName type, List<VariableDeclaration> variables) {
+  VariableDeclarationList.full(Comment comment, List<Annotation> metadata, Token keyword, TypeName type, List<VariableDeclaration> variables) : super.full(comment, metadata) {
     this._variables = new NodeList<VariableDeclaration>(this);
     this._keyword = keyword;
     this._type = becomeParentOf(type);
@@ -10744,20 +10793,14 @@
   }
   /**
    * Initialize a newly created variable declaration list.
+   * @param comment the documentation comment associated with this declaration list
+   * @param metadata the annotations associated with this declaration list
    * @param keyword the token representing the 'final', 'const' or 'var' keyword
    * @param type the type of the variables being declared
    * @param variables a list containing the individual variables being declared
    */
-  VariableDeclarationList({Token keyword, TypeName type, List<VariableDeclaration> variables}) : this.full(keyword, type, variables);
+  VariableDeclarationList({Comment comment, List<Annotation> metadata, Token keyword, TypeName type, List<VariableDeclaration> variables}) : this.full(comment, metadata, keyword, type, variables);
   accept(ASTVisitor visitor) => visitor.visitVariableDeclarationList(this);
-  Token get beginToken {
-    if (_keyword != null) {
-      return _keyword;
-    } else if (_type != null) {
-      return _type.beginToken;
-    }
-    return _variables.beginToken;
-  }
   Token get endToken => _variables.endToken;
   /**
    * Return the token representing the 'final', 'const' or 'var' keyword, or {@code null} if no
@@ -10791,8 +10834,8 @@
    * Set the token representing the 'final', 'const' or 'var' keyword to the given token.
    * @param keyword the token representing the 'final', 'const' or 'var' keyword
    */
-  void set keyword(Token keyword25) {
-    this._keyword = keyword25;
+  void set keyword(Token keyword26) {
+    this._keyword = keyword26;
   }
   /**
    * Set the type of the variables being declared to the given type name.
@@ -10805,6 +10848,14 @@
     safelyVisitChild(_type, visitor);
     _variables.accept(visitor);
   }
+  Token get firstTokenAfterCommentAndMetadata {
+    if (_keyword != null) {
+      return _keyword;
+    } else if (_type != null) {
+      return _type.beginToken;
+    }
+    return _variables.beginToken;
+  }
 }
 /**
  * Instances of the class {@code VariableDeclarationStatement} represent a list of variables that
@@ -10968,8 +11019,8 @@
    * Set the token representing the 'while' keyword to the given token.
    * @param keyword the token representing the 'while' keyword
    */
-  void set keyword(Token keyword26) {
-    this._keyword = keyword26;
+  void set keyword(Token keyword27) {
+    this._keyword = keyword27;
   }
   /**
    * Set the left parenthesis to the given token.
@@ -11375,10 +11426,13 @@
  */
 class ElementLocator_ElementMapper extends GeneralizingASTVisitor<Element> {
   Element visitBinaryExpression(BinaryExpression node) => node.element;
+  Element visitClassDeclaration(ClassDeclaration node) => node.element;
+  Element visitFunctionDeclaration(FunctionDeclaration node) => node.element;
   Element visitIdentifier(Identifier node) => node.element;
   Element visitImportDirective(ImportDirective node) => node.element;
   Element visitIndexExpression(IndexExpression node) => node.element;
   Element visitLibraryDirective(LibraryDirective node) => node.element;
+  Element visitMethodDeclaration(MethodDeclaration node) => node.element;
   Element visitPostfixExpression(PostfixExpression node) => node.element;
   Element visitPrefixedIdentifier(PrefixedIdentifier node) => node.element;
   Element visitPrefixExpression(PrefixExpression node) => node.element;
@@ -11389,6 +11443,7 @@
     }
     return null;
   }
+  Element visitVariableDeclaration(VariableDeclaration node) => node.element;
 }
 /**
  * Instances of the class {@code GeneralizingASTVisitor} implement an AST visitor that will
@@ -11500,6 +11555,7 @@
   R visitPrefixExpression(PrefixExpression node) => visitExpression(node);
   R visitPropertyAccess(PropertyAccess node) => visitExpression(node);
   R visitRedirectingConstructorInvocation(RedirectingConstructorInvocation node) => visitConstructorInitializer(node);
+  R visitRethrowExpression(RethrowExpression node) => visitExpression(node);
   R visitReturnStatement(ReturnStatement node) => visitStatement(node);
   R visitScriptTag(ScriptTag scriptTag) => visitNode(scriptTag);
   R visitShowCombinator(ShowCombinator node) => visitCombinator(node);
@@ -11559,10 +11615,10 @@
    * @param offset the offset used to identify the node
    */
   NodeLocator.con1(int offset) {
-    _jtd_constructor_118_impl(offset);
+    _jtd_constructor_119_impl(offset);
   }
-  _jtd_constructor_118_impl(int offset) {
-    _jtd_constructor_119_impl(offset, offset);
+  _jtd_constructor_119_impl(int offset) {
+    _jtd_constructor_120_impl(offset, offset);
   }
   /**
    * Initialize a newly created locator to locate one or more {@link ASTNode AST nodes} by locating
@@ -11572,9 +11628,9 @@
    * @param end the end offset of the range used to identify the node
    */
   NodeLocator.con2(int start, int end) {
-    _jtd_constructor_119_impl(start, end);
+    _jtd_constructor_120_impl(start, end);
   }
-  _jtd_constructor_119_impl(int start, int end) {
+  _jtd_constructor_120_impl(int start, int end) {
     this._startOffset = start;
     this._endOffset = end;
   }
@@ -11595,7 +11651,7 @@
     try {
       node.accept(this);
     } on NodeLocator_NodeFoundException catch (exception) {
-    } on JavaException catch (exception) {
+    } catch (exception) {
       AnalysisEngine.instance.logger.logInformation2("Unable to locate element at offset (${_startOffset} - ${_endOffset})", exception);
       return null;
     }
@@ -11606,7 +11662,7 @@
       node.visitChildren(this);
     } on NodeLocator_NodeFoundException catch (exception) {
       throw exception;
-    } on JavaException catch (exception) {
+    } catch (exception) {
       AnalysisEngine.instance.logger.logInformation2("Exception caught while traversing an AST structure.", exception);
     }
     int start = node.offset;
@@ -11932,6 +11988,10 @@
     node.visitChildren(this);
     return null;
   }
+  R visitRethrowExpression(RethrowExpression node) {
+    node.visitChildren(this);
+    return null;
+  }
   R visitReturnStatement(ReturnStatement node) {
     node.visitChildren(this);
     return null;
@@ -12115,6 +12175,7 @@
   R visitPrefixExpression(PrefixExpression node) => null;
   R visitPropertyAccess(PropertyAccess node) => null;
   R visitRedirectingConstructorInvocation(RedirectingConstructorInvocation node) => null;
+  R visitRethrowExpression(RethrowExpression node) => null;
   R visitReturnStatement(ReturnStatement node) => null;
   R visitScriptTag(ScriptTag node) => null;
   R visitShowCombinator(ShowCombinator node) => null;
@@ -12692,6 +12753,10 @@
     visit(node.argumentList);
     return null;
   }
+  Object visitRethrowExpression(RethrowExpression node) {
+    _writer.print("rethrow");
+    return null;
+  }
   Object visitReturnStatement(ReturnStatement node) {
     Expression expression14 = node.expression;
     if (expression14 == null) {
diff --git a/pkg/analyzer_experimental/lib/src/generated/constant.dart b/pkg/analyzer_experimental/lib/src/generated/constant.dart
index 9e82ce9..6dfbb47 100644
--- a/pkg/analyzer_experimental/lib/src/generated/constant.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/constant.dart
@@ -251,9 +251,9 @@
     return ValidResult.RESULT_OBJECT;
   }
   EvaluationResultImpl visitMethodInvocation(MethodInvocation node) {
-    Element element21 = node.methodName.element;
-    if (element21 is FunctionElement) {
-      FunctionElement function = element21 as FunctionElement;
+    Element element23 = node.methodName.element;
+    if (element23 is FunctionElement) {
+      FunctionElement function = element23 as FunctionElement;
       if (function.name == "identical") {
         NodeList<Expression> arguments3 = node.argumentList.arguments;
         if (arguments3.length == 2) {
@@ -363,9 +363,9 @@
    * @param errorCode the error code for the error to be generated
    */
   ErrorResult.con1(ASTNode node, ErrorCode errorCode) {
-    _jtd_constructor_158_impl(node, errorCode);
+    _jtd_constructor_157_impl(node, errorCode);
   }
-  _jtd_constructor_158_impl(ASTNode node, ErrorCode errorCode) {
+  _jtd_constructor_157_impl(ASTNode node, ErrorCode errorCode) {
     _errors.add(new ErrorResult_ErrorData(node, errorCode));
   }
   /**
@@ -375,9 +375,9 @@
    * @param secondResult the second set of results being merged
    */
   ErrorResult.con2(ErrorResult firstResult, ErrorResult secondResult) {
-    _jtd_constructor_159_impl(firstResult, secondResult);
+    _jtd_constructor_158_impl(firstResult, secondResult);
   }
-  _jtd_constructor_159_impl(ErrorResult firstResult, ErrorResult secondResult) {
+  _jtd_constructor_158_impl(ErrorResult firstResult, ErrorResult secondResult) {
     _errors.addAll(firstResult._errors);
     _errors.addAll(secondResult._errors);
   }
diff --git a/pkg/analyzer_experimental/lib/src/generated/element.dart b/pkg/analyzer_experimental/lib/src/generated/element.dart
index 79b1bc9..1a140b9 100644
--- a/pkg/analyzer_experimental/lib/src/generated/element.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/element.dart
@@ -483,6 +483,13 @@
    */
   FunctionType get type;
   /**
+   * Return {@code true} if this executable element is an operator. The test may be based on the
+   * name of the executable element, in which case the result will be correct when the name is
+   * legal.
+   * @return {@code true} if this executable element is an operator
+   */
+  bool isOperator();
+  /**
    * Return {@code true} if this element is a static element. A static element is an element that is
    * not associated with a particular instance, but rather with an entire library or class.
    * @return {@code true} if this executable element is a static element
@@ -761,12 +768,6 @@
    * @return {@code true} if this method is abstract
    */
   bool isAbstract();
-  /**
-   * Return {@code true} if this method is an operator. The test may be based on the name of the
-   * method, in which case the result will be correct when the name is legal.
-   * @return {@code true} if this method is an operator
-   */
-  bool isOperator();
 }
 /**
  * The interface {@code MultiplyDefinedElement} defines the behavior of pseudo-elements that
@@ -1675,7 +1676,7 @@
   LibraryElement get enclosingElement => super.enclosingElement as LibraryElement;
   List<FunctionElement> get functions => _functions;
   List<FunctionTypeAliasElement> get functionTypeAliases => _typeAliases;
-  String get identifier => source.fullName;
+  String get identifier => source.encoding;
   ElementKind get kind => ElementKind.COMPILATION_UNIT;
   Source get source => _source;
   List<TopLevelVariableElement> get topLevelVariables => _variables;
@@ -1706,8 +1707,8 @@
    * Set the source that corresponds to this compilation unit to the given source.
    * @param source the source that corresponds to this compilation unit
    */
-  void set source(Source source7) {
-    this._source = source7;
+  void set source(Source source5) {
+    this._source = source5;
   }
   /**
    * Set the top-level variables contained in this compilation unit to the given variables.
@@ -1951,10 +1952,10 @@
    * @param name the name of this element
    */
   ElementImpl.con1(Identifier name25) {
-    _jtd_constructor_174_impl(name25);
+    _jtd_constructor_178_impl(name25);
   }
-  _jtd_constructor_174_impl(Identifier name25) {
-    _jtd_constructor_175_impl(name25 == null ? "" : name25.name, name25 == null ? -1 : name25.offset);
+  _jtd_constructor_178_impl(Identifier name25) {
+    _jtd_constructor_179_impl(name25 == null ? "" : name25.name, name25 == null ? -1 : name25.offset);
   }
   /**
    * Initialize a newly created element to have the given name.
@@ -1963,9 +1964,9 @@
    * declaration of this element
    */
   ElementImpl.con2(String name8, int nameOffset2) {
-    _jtd_constructor_175_impl(name8, nameOffset2);
+    _jtd_constructor_179_impl(name8, nameOffset2);
   }
-  _jtd_constructor_175_impl(String name8, int nameOffset2) {
+  _jtd_constructor_179_impl(String name8, int nameOffset2) {
     this._name = name8;
     this._nameOffset = nameOffset2;
     this._modifiers = new Set();
@@ -2014,8 +2015,8 @@
    * Set the metadata associate with this element to the given array of annotations.
    * @param metadata the metadata to be associated with this element
    */
-  void set metadata(List<Annotation> metadata2) {
-    this._metadata = metadata2;
+  void set metadata(List<Annotation> metadata3) {
+    this._metadata = metadata3;
   }
   /**
    * Set the offset of the name of this element in the file that contains the declaration of this
@@ -2126,9 +2127,9 @@
    * @param element the element whose location is being represented
    */
   ElementLocationImpl.con1(Element element) {
-    _jtd_constructor_176_impl(element);
+    _jtd_constructor_180_impl(element);
   }
-  _jtd_constructor_176_impl(Element element) {
+  _jtd_constructor_180_impl(Element element) {
     List<String> components = new List<String>();
     Element ancestor = element;
     while (ancestor != null) {
@@ -2142,9 +2143,9 @@
    * @param encoding the encoded form of a location
    */
   ElementLocationImpl.con2(String encoding) {
-    _jtd_constructor_177_impl(encoding);
+    _jtd_constructor_181_impl(encoding);
   }
-  _jtd_constructor_177_impl(String encoding) {
+  _jtd_constructor_181_impl(String encoding) {
     this._components = decode(encoding);
   }
   bool operator ==(Object object) {
@@ -2283,9 +2284,9 @@
    * @param name the name of this element
    */
   ExecutableElementImpl.con1(Identifier name) : super.con1(name) {
-    _jtd_constructor_179_impl(name);
+    _jtd_constructor_183_impl(name);
   }
-  _jtd_constructor_179_impl(Identifier name) {
+  _jtd_constructor_183_impl(Identifier name) {
   }
   /**
    * Initialize a newly created executable element to have the given name.
@@ -2294,9 +2295,9 @@
    * declaration of this element
    */
   ExecutableElementImpl.con2(String name, int nameOffset) : super.con2(name, nameOffset) {
-    _jtd_constructor_180_impl(name, nameOffset);
+    _jtd_constructor_184_impl(name, nameOffset);
   }
-  _jtd_constructor_180_impl(String name, int nameOffset) {
+  _jtd_constructor_184_impl(String name, int nameOffset) {
   }
   ElementImpl getChild(String identifier27) {
     for (ExecutableElement function in _functions) {
@@ -2326,6 +2327,7 @@
   List<LocalVariableElement> get localVariables => _localVariables;
   List<ParameterElement> get parameters => _parameters;
   FunctionType get type => _type;
+  bool isOperator() => false;
   /**
    * Set the functions defined within this executable element to the given functions.
    * @param functions the functions defined within this executable element
@@ -2480,18 +2482,18 @@
    * @param name the name of this element
    */
   FieldElementImpl.con1(Identifier name) : super.con1(name) {
-    _jtd_constructor_183_impl(name);
+    _jtd_constructor_187_impl(name);
   }
-  _jtd_constructor_183_impl(Identifier name) {
+  _jtd_constructor_187_impl(Identifier name) {
   }
   /**
    * Initialize a newly created synthetic field element to have the given name.
    * @param name the name of this element
    */
   FieldElementImpl.con2(String name) : super.con2(name) {
-    _jtd_constructor_184_impl(name);
+    _jtd_constructor_188_impl(name);
   }
-  _jtd_constructor_184_impl(String name) {
+  _jtd_constructor_188_impl(String name) {
   }
   accept(ElementVisitor visitor) => visitor.visitFieldElement(this);
   ClassElement get enclosingElement => super.enclosingElement as ClassElement;
@@ -2527,9 +2529,9 @@
    * Initialize a newly created synthetic function element.
    */
   FunctionElementImpl() : super.con2("", -1) {
-    _jtd_constructor_185_impl();
+    _jtd_constructor_189_impl();
   }
-  _jtd_constructor_185_impl() {
+  _jtd_constructor_189_impl() {
     synthetic = true;
   }
   /**
@@ -2537,9 +2539,9 @@
    * @param name the name of this element
    */
   FunctionElementImpl.con1(Identifier name) : super.con1(name) {
-    _jtd_constructor_186_impl(name);
+    _jtd_constructor_190_impl(name);
   }
-  _jtd_constructor_186_impl(Identifier name) {
+  _jtd_constructor_190_impl(Identifier name) {
   }
   accept(ElementVisitor visitor) => visitor.visitFunctionElement(this);
   String get identifier => name;
@@ -2766,8 +2768,8 @@
    * Set the source that corresponds to this HTML file to the given source.
    * @param source the source that corresponds to this HTML file
    */
-  void set source(Source source8) {
-    this._source = source8;
+  void set source(Source source6) {
+    this._source = source6;
   }
   void visitChildren(ElementVisitor<Object> visitor) {
     super.visitChildren(visitor);
@@ -2990,17 +2992,21 @@
     Set<LibraryElement> libraries = new Set<LibraryElement>();
     for (ExportElement element in _exports) {
       LibraryElement library = element.exportedLibrary;
-      javaSetAdd(libraries, library);
+      if (library != null) {
+        javaSetAdd(libraries, library);
+      }
     }
     return new List.from(libraries);
   }
   List<ExportElement> get exports => _exports;
-  String get identifier => _definingCompilationUnit.source.fullName;
+  String get identifier => _definingCompilationUnit.source.encoding;
   List<LibraryElement> get importedLibraries {
     Set<LibraryElement> libraries = new Set<LibraryElement>();
     for (ImportElement element in _imports) {
-      LibraryElement prefix = element.importedLibrary;
-      javaSetAdd(libraries, prefix);
+      LibraryElement library = element.importedLibrary;
+      if (library != null) {
+        javaSetAdd(libraries, library);
+      }
     }
     return new List.from(libraries);
   }
@@ -3017,6 +3023,12 @@
     }
     return new List.from(prefixes);
   }
+  Source get source {
+    if (_definingCompilationUnit == null) {
+      return null;
+    }
+    return _definingCompilationUnit.source;
+  }
   int get hashCode => _definingCompilationUnit.hashCode;
   bool isBrowserApplication() => _entryPoint != null && isOrImportsBrowserLibrary();
   bool isDartCore() => name == "dart.core";
@@ -3090,8 +3102,8 @@
     visited.add(this);
     for (int index = 0; index < visited.length; index++) {
       LibraryElement library = visited[index];
-      Source source12 = library.definingCompilationUnit.source;
-      if (source12 == htmlLibSource) {
+      Source source10 = library.definingCompilationUnit.source;
+      if (source10 == htmlLibSource) {
         return true;
       }
       for (LibraryElement importedLibrary in library.importedLibraries) {
@@ -3171,9 +3183,9 @@
    * @param name the name of this element
    */
   MethodElementImpl.con1(Identifier name) : super.con1(name) {
-    _jtd_constructor_195_impl(name);
+    _jtd_constructor_199_impl(name);
   }
-  _jtd_constructor_195_impl(Identifier name) {
+  _jtd_constructor_199_impl(Identifier name) {
   }
   /**
    * Initialize a newly created method element to have the given name.
@@ -3182,9 +3194,9 @@
    * declaration of this element
    */
   MethodElementImpl.con2(String name, int nameOffset) : super.con2(name, nameOffset) {
-    _jtd_constructor_196_impl(name, nameOffset);
+    _jtd_constructor_200_impl(name, nameOffset);
   }
-  _jtd_constructor_196_impl(String name, int nameOffset) {
+  _jtd_constructor_200_impl(String name, int nameOffset) {
   }
   accept(ElementVisitor visitor) => visitor.visitMethodElement(this);
   ClassElement get enclosingElement => super.enclosingElement as ClassElement;
@@ -3467,9 +3479,9 @@
    * @param name the name of this element
    */
   PropertyAccessorElementImpl.con1(Identifier name) : super.con1(name) {
-    _jtd_constructor_201_impl(name);
+    _jtd_constructor_205_impl(name);
   }
-  _jtd_constructor_201_impl(Identifier name) {
+  _jtd_constructor_205_impl(Identifier name) {
   }
   /**
    * Initialize a newly created synthetic property accessor element to be associated with the given
@@ -3477,9 +3489,9 @@
    * @param variable the variable with which this access is associated
    */
   PropertyAccessorElementImpl.con2(PropertyInducingElementImpl variable2) : super.con2(variable2.name, -1) {
-    _jtd_constructor_202_impl(variable2);
+    _jtd_constructor_206_impl(variable2);
   }
-  _jtd_constructor_202_impl(PropertyInducingElementImpl variable2) {
+  _jtd_constructor_206_impl(PropertyInducingElementImpl variable2) {
     this._variable = variable2;
     synthetic = true;
   }
@@ -3544,18 +3556,18 @@
    * @param name the name of this element
    */
   PropertyInducingElementImpl.con1(Identifier name) : super.con1(name) {
-    _jtd_constructor_203_impl(name);
+    _jtd_constructor_207_impl(name);
   }
-  _jtd_constructor_203_impl(Identifier name) {
+  _jtd_constructor_207_impl(Identifier name) {
   }
   /**
    * Initialize a newly created synthetic element to have the given name.
    * @param name the name of this element
    */
   PropertyInducingElementImpl.con2(String name) : super.con2(name, -1) {
-    _jtd_constructor_204_impl(name);
+    _jtd_constructor_208_impl(name);
   }
-  _jtd_constructor_204_impl(String name) {
+  _jtd_constructor_208_impl(String name) {
     synthetic = true;
   }
   PropertyAccessorElement get getter => _getter;
@@ -3626,18 +3638,18 @@
    * @param name the name of this element
    */
   TopLevelVariableElementImpl.con1(Identifier name) : super.con1(name) {
-    _jtd_constructor_206_impl(name);
+    _jtd_constructor_210_impl(name);
   }
-  _jtd_constructor_206_impl(Identifier name) {
+  _jtd_constructor_210_impl(Identifier name) {
   }
   /**
    * Initialize a newly created synthetic top-level variable element to have the given name.
    * @param name the name of this element
    */
   TopLevelVariableElementImpl.con2(String name) : super.con2(name) {
-    _jtd_constructor_207_impl(name);
+    _jtd_constructor_211_impl(name);
   }
-  _jtd_constructor_207_impl(String name) {
+  _jtd_constructor_211_impl(String name) {
   }
   accept(ElementVisitor visitor) => visitor.visitTopLevelVariableElement(this);
   ElementKind get kind => ElementKind.TOP_LEVEL_VARIABLE;
@@ -3716,9 +3728,9 @@
    * @param name the name of this element
    */
   VariableElementImpl.con1(Identifier name) : super.con1(name) {
-    _jtd_constructor_209_impl(name);
+    _jtd_constructor_213_impl(name);
   }
-  _jtd_constructor_209_impl(Identifier name) {
+  _jtd_constructor_213_impl(Identifier name) {
   }
   /**
    * Initialize a newly created variable element to have the given name.
@@ -3727,9 +3739,9 @@
    * declaration of this element
    */
   VariableElementImpl.con2(String name, int nameOffset) : super.con2(name, nameOffset) {
-    _jtd_constructor_210_impl(name, nameOffset);
+    _jtd_constructor_214_impl(name, nameOffset);
   }
-  _jtd_constructor_210_impl(String name, int nameOffset) {
+  _jtd_constructor_214_impl(String name, int nameOffset) {
   }
   /**
    * Return the result of evaluating this variable's initializer as a compile-time constant
@@ -3922,9 +3934,9 @@
    * @param element the element representing the declaration of the function type
    */
   FunctionTypeImpl.con1(ExecutableElement element) : super(element, element == null ? null : element.name) {
-    _jtd_constructor_261_impl(element);
+    _jtd_constructor_265_impl(element);
   }
-  _jtd_constructor_261_impl(ExecutableElement element) {
+  _jtd_constructor_265_impl(ExecutableElement element) {
   }
   /**
    * Initialize a newly created function type to be declared by the given element and to have the
@@ -3932,9 +3944,9 @@
    * @param element the element representing the declaration of the function type
    */
   FunctionTypeImpl.con2(FunctionTypeAliasElement element) : super(element, element == null ? null : element.name) {
-    _jtd_constructor_262_impl(element);
+    _jtd_constructor_266_impl(element);
   }
-  _jtd_constructor_262_impl(FunctionTypeAliasElement element) {
+  _jtd_constructor_266_impl(FunctionTypeAliasElement element) {
   }
   bool operator ==(Object object) {
     if (object is! FunctionTypeImpl) {
@@ -3949,11 +3961,11 @@
   Type2 get returnType => _returnType;
   List<Type2> get typeArguments => _typeArguments;
   int get hashCode {
-    Element element40 = element;
-    if (element40 == null) {
+    Element element44 = element;
+    if (element44 == null) {
       return 0;
     }
-    return element40.hashCode;
+    return element44.hashCode;
   }
   bool isSubtypeOf(Type2 type) {
     if (type == null) {
@@ -4064,8 +4076,8 @@
     if (argumentTypes.length == 0) {
       return this;
     }
-    Element element41 = element;
-    FunctionTypeImpl newType = (element41 is ExecutableElement) ? new FunctionTypeImpl.con1((element41 as ExecutableElement)) : new FunctionTypeImpl.con2((element41 as FunctionTypeAliasElement));
+    Element element45 = element;
+    FunctionTypeImpl newType = (element45 is ExecutableElement) ? new FunctionTypeImpl.con1((element45 as ExecutableElement)) : new FunctionTypeImpl.con2((element45 as FunctionTypeAliasElement));
     newType.returnType = _returnType.substitute2(argumentTypes, parameterTypes);
     newType.normalParameterTypes = TypeImpl.substitute(_normalParameterTypes, argumentTypes, parameterTypes);
     newType.optionalParameterTypes = TypeImpl.substitute(_optionalParameterTypes, argumentTypes, parameterTypes);
@@ -4198,9 +4210,9 @@
    * @see #getLeastUpperBound(Type)
    */
   static Set<InterfaceType> computeSuperinterfaceSet2(InterfaceType type, Set<InterfaceType> set) {
-    Element element42 = type.element;
-    if (element42 != null && element42 is ClassElement) {
-      ClassElement classElement = element42 as ClassElement;
+    Element element46 = type.element;
+    if (element46 != null && element46 is ClassElement) {
+      ClassElement classElement = element46 as ClassElement;
       List<InterfaceType> superinterfaces = classElement.interfaces;
       for (InterfaceType superinterface in superinterfaces) {
         javaSetAdd(set, superinterface);
@@ -4223,9 +4235,9 @@
    * @param element the element representing the declaration of the type
    */
   InterfaceTypeImpl.con1(ClassElement element) : super(element, element.name) {
-    _jtd_constructor_263_impl(element);
+    _jtd_constructor_267_impl(element);
   }
-  _jtd_constructor_263_impl(ClassElement element) {
+  _jtd_constructor_267_impl(ClassElement element) {
   }
   /**
    * Initialize a newly created type to have the given name. This constructor should only be used in
@@ -4233,9 +4245,9 @@
    * @param name the name of the type
    */
   InterfaceTypeImpl.con2(String name) : super(null, name) {
-    _jtd_constructor_264_impl(name);
+    _jtd_constructor_268_impl(name);
   }
-  _jtd_constructor_264_impl(String name) {
+  _jtd_constructor_268_impl(String name) {
   }
   bool operator ==(Object object) {
     if (object is! InterfaceTypeImpl) {
@@ -4291,18 +4303,18 @@
   }
   List<Type2> get typeArguments => _typeArguments;
   int get hashCode {
-    ClassElement element43 = element;
-    if (element43 == null) {
+    ClassElement element47 = element;
+    if (element47 == null) {
       return 0;
     }
-    return element43.hashCode;
+    return element47.hashCode;
   }
   bool isDartCoreFunction() {
-    ClassElement element44 = element;
-    if (element44 == null) {
+    ClassElement element48 = element;
+    if (element48 == null) {
       return false;
     }
-    return element44.name == "Function" && element44.library.isDartCore();
+    return element48.name == "Function" && element48.library.isDartCore();
   }
   bool isDirectSupertypeOf(InterfaceType type) {
     ClassElement i = element;
diff --git a/pkg/analyzer_experimental/lib/src/generated/engine.dart b/pkg/analyzer_experimental/lib/src/generated/engine.dart
index 02832e5..6b0bdad 100644
--- a/pkg/analyzer_experimental/lib/src/generated/engine.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/engine.dart
@@ -12,8 +12,8 @@
 import 'ast.dart' show CompilationUnit, Directive, PartOfDirective;
 import 'parser.dart' show Parser;
 import 'element.dart';
-import 'resolver.dart' show Namespace, NamespaceBuilder, LibraryResolver;
-import 'html.dart' show HtmlScanner, HtmlScanResult, HtmlParser, HtmlParseResult;
+import 'resolver.dart' show Namespace, NamespaceBuilder, LibraryResolver, HtmlUnitBuilder;
+import 'html.dart' show XmlTagNode, XmlAttributeNode, SimpleXmlVisitor, HtmlScanner, HtmlScanResult, HtmlParser, HtmlParseResult, HtmlUnit;
 
 /**
  * The unique instance of the class {@code AnalysisEngine} serves as the entry point for the
@@ -96,15 +96,30 @@
 }
 /**
  * The interface {@code AnalysisContext} defines the behavior of objects that represent a context in
- * which analysis can be performed. The context includes such information as the version of the SDK
- * being analyzed against as well as the package-root used to resolve 'package:' URI's. (Both of
- * which are known indirectly through the {@link SourceFactory source factory}.)
+ * which a single analysis can be performed and incrementally maintained. The context includes such
+ * information as the version of the SDK being analyzed against as well as the package-root used to
+ * resolve 'package:' URI's. (Both of which are known indirectly through the {@link SourceFactorysource factory}.)
  * <p>
- * They also represent the state of a given analysis, which includes knowing which sources have been
- * included in the analysis (either directly or indirectly) and the results of the analysis. Some
- * analysis results are cached in order to allow the context to balance between memory usage and
- * performance. TODO(brianwilkerson) Decide how this is reflected in the API: a getFoo() and
- * getOrComputeFoo() pair of methods, or a single getFoo(boolean).
+ * An analysis context also represents the state of the analysis, which includes knowing which
+ * sources have been included in the analysis (either directly or indirectly) and the results of the
+ * analysis. Sources must be added and removed from the context using the method{@link #applyChanges(ChangeSet)}, which is also used to notify the context when sources have been
+ * modified and, consequently, previously known results might have been invalidated.
+ * <p>
+ * There are two ways to access the results of the analysis. The most common is to use one of the
+ * 'get' methods to access the results. The 'get' methods have the advantage that they will always
+ * return quickly, but have the disadvantage that if the results are not currently available they
+ * will return either nothing or in some cases an incomplete result. The second way to access
+ * results is by using one of the 'compute' methods. The 'compute' methods will always attempt to
+ * compute the requested results but might block the caller for a significant period of time.
+ * <p>
+ * When results have been invalidated, have never been computed (as is the case for newly added
+ * sources), or have been removed from the cache, they are <b>not</b> automatically recreated. They
+ * will only be recreated if one of the 'compute' methods is invoked.
+ * <p>
+ * However, this is not always acceptable. Some clients need to keep the analysis results
+ * up-to-date. For such clients there is a mechanism that allows them to incrementally perform
+ * needed analysis and get notified of the consequent changes to the analysis results. This
+ * mechanism is realized by the method {@link #performAnalysisTask()}.
  * <p>
  * Analysis engine allows for having more than one context. This can be used, for example, to
  * perform one analysis based on the state of files on disk and a separate analysis based on the
@@ -119,6 +134,61 @@
    */
   void applyChanges(ChangeSet changeSet);
   /**
+   * Return an array containing all of the errors associated with the given source. If the errors
+   * are not already known then the source will be analyzed in order to determine the errors
+   * associated with it.
+   * @param source the source whose errors are to be returned
+   * @return all of the errors associated with the given source
+   * @throws AnalysisException if the errors could not be determined because the analysis could not
+   * be performed
+   * @see #getErrors(Source)
+   */
+  List<AnalysisError> computeErrors(Source source);
+  /**
+   * Return the element model corresponding to the HTML file defined by the given source. If the
+   * element model does not yet exist it will be created. The process of creating an element model
+   * for an HTML file can long-running, depending on the size of the file and the number of
+   * libraries that are defined in it (via script tags) that also need to have a model built for
+   * them.
+   * @param source the source defining the HTML file whose element model is to be returned
+   * @return the element model corresponding to the HTML file defined by the given source
+   * @throws AnalysisException if the element model could not be determined because the analysis
+   * could not be performed
+   * @see #getHtmlElement(Source)
+   */
+  HtmlElement computeHtmlElement(Source source);
+  /**
+   * Return the kind of the given source, computing it's kind if it is not already known. Return{@link SourceKind#UNKNOWN} if the source is not contained in this context.
+   * @param source the source whose kind is to be returned
+   * @return the kind of the given source
+   * @see #getKindOf(Source)
+   */
+  SourceKind computeKindOf(Source source);
+  /**
+   * Return the element model corresponding to the library defined by the given source. If the
+   * element model does not yet exist it will be created. The process of creating an element model
+   * for a library can long-running, depending on the size of the library and the number of
+   * libraries that are imported into it that also need to have a model built for them.
+   * @param source the source defining the library whose element model is to be returned
+   * @return the element model corresponding to the library defined by the given source
+   * @throws AnalysisException if the element model could not be determined because the analysis
+   * could not be performed
+   * @see #getLibraryElement(Source)
+   */
+  LibraryElement computeLibraryElement(Source source);
+  /**
+   * Return the line information for the given source, or {@code null} if the source is not of a
+   * recognized kind (neither a Dart nor HTML file). If the line information was not previously
+   * known it will be created. The line information is used to map offsets from the beginning of the
+   * source to line and column pairs.
+   * @param source the source whose line information is to be returned
+   * @return the line information for the given source
+   * @throws AnalysisException if the line information could not be determined because the analysis
+   * could not be performed
+   * @see #getLineInfo(Source)
+   */
+  LineInfo computeLineInfo(Source source);
+  /**
    * Create a new context in which analysis can be performed. Any sources in the specified container
    * will be removed from this context and added to the newly created context.
    * @param container the container containing sources that should be removed from this context and
@@ -127,7 +197,11 @@
    */
   AnalysisContext extractContext(SourceContainer container);
   /**
-   * Return the element referenced by the given location.
+   * Return the element referenced by the given location, or {@code null} if the element is not
+   * immediately available or if there is no element with the given location. The latter condition
+   * can occur, for example, if the location describes an element from a different context or if the
+   * element has been removed from this context as a result of some change since it was originally
+   * obtained.
    * @param location the reference describing the element to be returned
    * @return the element referenced by the given location
    */
@@ -135,43 +209,55 @@
   /**
    * Return an array containing all of the errors associated with the given source. The array will
    * be empty if the source is not known to this context or if there are no errors in the source.
+   * The errors contained in the array can be incomplete.
    * @param source the source whose errors are to be returned
    * @return all of the errors associated with the given source
-   * @throws AnalysisException if the errors could not be determined because the analysis could not
-   * be performed
+   * @see #computeErrors(Source)
    */
   List<AnalysisError> getErrors(Source source);
   /**
-   * Return the element model corresponding to the HTML file defined by the given source.
+   * Return the element model corresponding to the HTML file defined by the given source, or{@code null} if the source does not represent an HTML file, the element representing the file
+   * has not yet been created, or the analysis of the HTML file failed for some reason.
    * @param source the source defining the HTML file whose element model is to be returned
    * @return the element model corresponding to the HTML file defined by the given source
+   * @see #computeHtmlElement(Source)
    */
   HtmlElement getHtmlElement(Source source);
   /**
+   * Return the sources for the HTML files that reference the given compilation unit. If the source
+   * does not represent a Dart source or is not known to this context, the returned array will be
+   * empty. The contents of the array can be incomplete.
+   * @param source the source referenced by the returned HTML files
+   * @return the sources for the HTML files that reference the given compilation unit
+   */
+  List<Source> getHtmlFilesReferencing(Source source);
+  /**
    * Return an array containing all of the sources known to this context that represent HTML files.
+   * The contents of the array can be incomplete.
    * @return the sources known to this context that represent HTML files
    */
   List<Source> get htmlSources;
   /**
-   * Return the kind of the given source if it is already known, or {@code null} if the kind is not
-   * already known.
+   * Return the kind of the given source, or {@code null} if the kind is not known to this context.
    * @param source the source whose kind is to be returned
    * @return the kind of the given source
-   * @see #getOrComputeKindOf(Source)
+   * @see #computeKindOf(Source)
    */
-  SourceKind getKnownKindOf(Source source);
+  SourceKind getKindOf(Source source);
   /**
    * Return an array containing all of the sources known to this context that represent the defining
    * compilation unit of a library that can be run within a browser. The sources that are returned
    * represent libraries that have a 'main' method and are either referenced by an HTML file or
-   * import, directly or indirectly, a client-only library.
+   * import, directly or indirectly, a client-only library. The contents of the array can be
+   * incomplete.
    * @return the sources known to this context that represent the defining compilation unit of a
    * library that can be run within a browser
    */
   List<Source> get launchableClientLibrarySources;
   /**
    * Return an array containing all of the sources known to this context that represent the defining
-   * compilation unit of a library that can be run outside of a browser.
+   * compilation unit of a library that can be run outside of a browser. The contents of the array
+   * can be incomplete.
    * @return the sources known to this context that represent the defining compilation unit of a
    * library that can be run outside of a browser
    */
@@ -183,48 +269,64 @@
    * multiple identically named libraries. If the source represents the defining compilation unit of
    * a library, then the returned array will contain the given source as its only element. If the
    * source does not represent a Dart source or is not known to this context, the returned array
-   * will be empty.
+   * will be empty. The contents of the array can be incomplete.
    * @param source the source contained in the returned libraries
    * @return the sources for the libraries containing the given source
    */
   List<Source> getLibrariesContaining(Source source);
   /**
-   * Return the element model corresponding to the library defined by the given source. If the
-   * element model does not yet exist it will be created. The process of creating an element model
-   * for a library can long-running, depending on the size of the library and the number of
-   * libraries that are imported into it that also need to have a model built for them.
-   * @param source the source defining the library whose element model is to be returned
-   * @return the element model corresponding to the library defined by the given source or{@code null} if the element model could not be determined because the analysis could
-   * not be performed
-   */
-  LibraryElement getLibraryElement(Source source);
-  /**
-   * Return the element model corresponding to the library defined by the given source, or{@code null} if the element model does not currently exist or if the analysis could not be
-   * performed.
+   * Return the element model corresponding to the library defined by the given source, or{@code null} if the element model does not currently exist or if the library cannot be analyzed
+   * for some reason.
    * @param source the source defining the library whose element model is to be returned
    * @return the element model corresponding to the library defined by the given source
    */
-  LibraryElement getLibraryElementOrNull(Source source);
+  LibraryElement getLibraryElement(Source source);
   /**
    * Return an array containing all of the sources known to this context that represent the defining
-   * compilation unit of a library.
+   * compilation unit of a library. The contents of the array can be incomplete.
    * @return the sources known to this context that represent the defining compilation unit of a
    * library
    */
   List<Source> get librarySources;
   /**
-   * Return the kind of the given source, computing it's kind if it is not already known.
-   * @param source the source whose kind is to be returned
-   * @return the kind of the given source
-   * @see #getKnownKindOf(Source)
+   * Return the line information for the given source, or {@code null} if the line information is
+   * not known. The line information is used to map offsets from the beginning of the source to line
+   * and column pairs.
+   * @param source the source whose line information is to be returned
+   * @return the line information for the given source
+   * @see #computeLineInfo(Source)
    */
-  SourceKind getOrComputeKindOf(Source source);
+  LineInfo getLineInfo(Source source);
   /**
    * Return the source factory used to create the sources that can be analyzed in this context.
    * @return the source factory used to create the sources that can be analyzed in this context
    */
   SourceFactory get sourceFactory;
   /**
+   * Return {@code true} if the given source is known to be the defining compilation unit of a
+   * library that can be run on a client (references 'dart:html', either directly or indirectly).
+   * <p>
+   * <b>Note:</b> In addition to the expected case of returning {@code false} if the source is known
+   * to be a library that cannot be run on a client, this method will also return {@code false} if
+   * the source is not known to be a library or if we do not know whether it can be run on a client.
+   * @param librarySource the source being tested
+   * @return {@code true} if the given source is known to be a library that can be run on a client
+   */
+  bool isClientLibrary(Source librarySource);
+  /**
+   * Return {@code true} if the given source is known to be the defining compilation unit of a
+   * library that can be run on the server (does not reference 'dart:html', either directly or
+   * indirectly).
+   * <p>
+   * <b>Note:</b> In addition to the expected case of returning {@code false} if the source is known
+   * to be a library that cannot be run on the server, this method will also return {@code false} if
+   * the source is not known to be a library or if we do not know whether it can be run on the
+   * server.
+   * @param librarySource the source being tested
+   * @return {@code true} if the given source is known to be a library that can be run on the server
+   */
+  bool isServerLibrary(Source librarySource);
+  /**
    * Add the sources contained in the specified context to this context's collection of sources.
    * This method is called when an existing context's pubspec has been removed, and the contained
    * sources should be reanalyzed as part of this context.
@@ -238,7 +340,7 @@
    * @return the AST structure representing the content of the source
    * @throws AnalysisException if the analysis could not be performed
    */
-  CompilationUnit parse(Source source);
+  CompilationUnit parseCompilationUnit(Source source);
   /**
    * Parse a single HTML source to produce an AST structure. The resulting HTML AST structure may or
    * may not be resolved, and may have a slightly different structure depending upon whether it is
@@ -247,22 +349,49 @@
    * @return the parse result (not {@code null})
    * @throws AnalysisException if the analysis could not be performed
    */
-  HtmlParseResult parseHtml(Source source);
+  HtmlUnit parseHtmlUnit(Source source);
   /**
    * Perform the next unit of work required to keep the analysis results up-to-date and return
    * information about the consequent changes to the analysis results. If there were no results the
-   * returned array will be empty. This method can be long running.
+   * returned array will be empty. If there are no more units of work required, then this method
+   * returns {@code null}. This method can be long running.
    * @return an array containing notices of changes to the analysis results
    */
   List<ChangeNotice> performAnalysisTask();
   /**
    * Parse and resolve a single source within the given context to produce a fully resolved AST.
-   * @param source the source to be parsed and resolved
-   * @param library the library defining the context in which the source file is to be resolved
+   * @param unitSource the source to be parsed and resolved
+   * @param library the library containing the source to be resolved
+   * @return the result of resolving the AST structure representing the content of the source in the
+   * context of the given library
+   * @throws AnalysisException if the analysis could not be performed
+   */
+  CompilationUnit resolveCompilationUnit(Source unitSource, LibraryElement library);
+  /**
+   * Parse and resolve a single source within the given context to produce a fully resolved AST.
+   * @param unitSource the source to be parsed and resolved
+   * @param librarySource the source of the defining compilation unit of the library containing the
+   * source to be resolved
+   * @return the result of resolving the AST structure representing the content of the source in the
+   * context of the given library
+   * @throws AnalysisException if the analysis could not be performed
+   */
+  CompilationUnit resolveCompilationUnit2(Source unitSource, Source librarySource);
+  /**
+   * Parse and resolve a single source within the given context to produce a fully resolved AST.
+   * @param htmlSource the source to be parsed and resolved
    * @return the result of resolving the AST structure representing the content of the source
    * @throws AnalysisException if the analysis could not be performed
    */
-  CompilationUnit resolve(Source source, LibraryElement library);
+  HtmlUnit resolveHtmlUnit(Source htmlSource);
+  /**
+   * Set the contents of the given source to the given contents and mark the source as having
+   * changed. This has the effect of overriding the default contents of the source. If the contents
+   * are {@code null} the override is removed so that the default contents will be returned.
+   * @param source the source whose contents are being overridden
+   * @param contents the new contents of the source
+   */
+  void setContents(Source source, String contents);
   /**
    * Set the source factory used to create the sources that can be analyzed in this context to the
    * given source factory. Clients can safely assume that all analysis results have been
@@ -288,18 +417,18 @@
    * Initialize a newly created exception.
    */
   AnalysisException() : super() {
-    _jtd_constructor_123_impl();
+    _jtd_constructor_124_impl();
   }
-  _jtd_constructor_123_impl() {
+  _jtd_constructor_124_impl() {
   }
   /**
    * Initialize a newly created exception to have the given message.
    * @param message the message associated with the exception
    */
   AnalysisException.con1(String message) : super(message) {
-    _jtd_constructor_124_impl(message);
+    _jtd_constructor_125_impl(message);
   }
-  _jtd_constructor_124_impl(String message) {
+  _jtd_constructor_125_impl(String message) {
   }
   /**
    * Initialize a newly created exception to have the given message and cause.
@@ -307,98 +436,49 @@
    * @param cause the underlying exception that caused this exception
    */
   AnalysisException.con2(String message, Exception cause) : super(message, cause) {
-    _jtd_constructor_125_impl(message, cause);
+    _jtd_constructor_126_impl(message, cause);
   }
-  _jtd_constructor_125_impl(String message, Exception cause) {
+  _jtd_constructor_126_impl(String message, Exception cause) {
   }
   /**
    * Initialize a newly created exception to have the given cause.
    * @param cause the underlying exception that caused this exception
    */
   AnalysisException.con3(Exception cause) : super.withCause(cause) {
-    _jtd_constructor_126_impl(cause);
+    _jtd_constructor_127_impl(cause);
   }
-  _jtd_constructor_126_impl(Exception cause) {
+  _jtd_constructor_127_impl(Exception cause) {
   }
 }
 /**
- * Instances of the class {@code ChangeNotice} represent a change to the analysis results associated
- * with a given source.
+ * The interface {@code ChangeNotice} defines the behavior of objects that represent a change to the
+ * analysis results associated with a given source.
+ * @coverage dart.engine
  */
-class ChangeNotice {
-  /**
-   * The source for which the result is being reported.
-   */
-  Source _source;
-  /**
-   * The fully resolved AST that changed as a result of the analysis, or {@code null} if the AST was
-   * not changed.
-   */
-  CompilationUnit _compilationUnit;
-  /**
-   * The errors that changed as a result of the analysis, or {@code null} if errors were not
-   * changed.
-   */
-  List<AnalysisError> _errors;
-  /**
-   * The line information associated with the source, or {@code null} if errors were not changed.
-   */
-  LineInfo _lineInfo;
-  /**
-   * An empty array of change notices.
-   */
-  static List<ChangeNotice> EMPTY_ARRAY = new List<ChangeNotice>(0);
-  /**
-   * Initialize a newly created result representing the fact that the errors associated with a
-   * source have changed.
-   * @param source the source for which the result is being reported
-   * @param errors the errors that changed as a result of the analysis
-   * @param the line information associated with the source
-   */
-  ChangeNotice.con1(Source source2, List<AnalysisError> errors2, LineInfo lineInfo3) {
-    _jtd_constructor_127_impl(source2, errors2, lineInfo3);
-  }
-  _jtd_constructor_127_impl(Source source2, List<AnalysisError> errors2, LineInfo lineInfo3) {
-    this._source = source2;
-    this._errors = errors2;
-    this._lineInfo = lineInfo3;
-  }
-  /**
-   * Initialize a newly created result representing the fact that the resolution of a source has
-   * changed.
-   * @param source the source for which the result is being reported
-   * @param compilationUnit the fully resolved AST produced as a result of the analysis
-   */
-  ChangeNotice.con2(Source source3, CompilationUnit compilationUnit9) {
-    _jtd_constructor_128_impl(source3, compilationUnit9);
-  }
-  _jtd_constructor_128_impl(Source source3, CompilationUnit compilationUnit9) {
-    this._source = source3;
-    this._compilationUnit = compilationUnit9;
-  }
+abstract class ChangeNotice {
   /**
    * Return the fully resolved AST that changed as a result of the analysis, or {@code null} if the
    * AST was not changed.
    * @return the fully resolved AST that changed as a result of the analysis
    */
-  CompilationUnit get compilationUnit => _compilationUnit;
+  CompilationUnit get compilationUnit;
   /**
    * Return the errors that changed as a result of the analysis, or {@code null} if errors were not
    * changed.
    * @return the errors that changed as a result of the analysis
    */
-  List<AnalysisError> get errors => _errors;
+  List<AnalysisError> get errors;
   /**
    * Return the line information associated with the source, or {@code null} if errors were not
    * changed.
    * @return the line information associated with the source
    */
-  LineInfo get lineInfo => _lineInfo;
+  LineInfo get lineInfo;
   /**
    * Return the source for which the result is being reported.
    * @return the source for which the result is being reported
    */
-  Source get source => _source;
+  Source get source;
 }
 /**
  * Instances of the class {@code ChangeSet} indicate what sources have been added, changed, or
@@ -407,15 +487,15 @@
  */
 class ChangeSet {
   /**
-   * A table mapping the sources that have been added to their contents.
+   * A list containing the sources that have been added.
    */
-  Map<Source, String> _added3 = new Map<Source, String>();
+  List<Source> _added2 = new List<Source>();
   /**
-   * A table mapping the sources that have been changed to their contents.
+   * A list containing the sources that have been changed.
    */
-  Map<Source, String> _changed3 = new Map<Source, String>();
+  List<Source> _changed2 = new List<Source>();
   /**
-   * A list containing the sources that have been removed..
+   * A list containing the sources that have been removed.
    */
   List<Source> _removed2 = new List<Source>();
   /**
@@ -433,20 +513,7 @@
    * @param source the source that was added
    */
   void added(Source source) {
-    added2(source, null);
-  }
-  /**
-   * Record that the specified source has been added and that it has the given content. If the
-   * content is non-{@code null}, this has the effect of overriding the default contents of the
-   * source. If the contents are {@code null}, any previous override is removed so that the default
-   * contents will be used.
-   * @param source the source that was added
-   * @param content the content of the new source
-   */
-  void added2(Source source, String content) {
-    if (source != null) {
-      _added3[source] = content;
-    }
+    _added2.add(source);
   }
   /**
    * Record that the specified source has been changed and that it's content is the default contents
@@ -454,31 +521,18 @@
    * @param source the source that was changed
    */
   void changed(Source source) {
-    changed2(source, null);
+    _changed2.add(source);
   }
   /**
-   * Record that the specified source has been changed and that it now has the given content. If the
-   * content is non-{@code null}, this has the effect of overriding the default contents of the
-   * source. If the contents are {@code null}, any previous override is removed so that the default
-   * contents will be used.
-   * @param source the source that was changed
-   * @param content the new content of the source
+   * Return a collection of the sources that have been added.
+   * @return a collection of the sources that have been added
    */
-  void changed2(Source source, String content) {
-    if (source != null) {
-      _changed3[source] = content;
-    }
-  }
+  List<Source> get added3 => _added2;
   /**
-   * Return a table mapping the sources that have been added to their contents.
-   * @return a table mapping the sources that have been added to their contents
+   * Return a collection of sources that have been changed.
+   * @return a collection of sources that have been changed
    */
-  Map<Source, String> get addedWithContent => _added3;
-  /**
-   * Return a table mapping the sources that have been changed to their contents.
-   * @return a table mapping the sources that have been changed to their contents
-   */
-  Map<Source, String> get changedWithContent => _changed3;
+  List<Source> get changed3 => _changed2;
   /**
    * Return a list containing the sources that were removed.
    * @return a list containing the sources that were removed
@@ -493,7 +547,7 @@
    * Return {@code true} if this change set does not contain any changes.
    * @return {@code true} if this change set does not contain any changes
    */
-  bool isEmpty() => _added3.isEmpty && _changed3.isEmpty && _removed2.isEmpty && _removedContainers.isEmpty;
+  bool isEmpty() => _added2.isEmpty && _changed2.isEmpty && _removed2.isEmpty && _removedContainers.isEmpty;
   /**
    * Record that the specified source has been removed.
    * @param source the source that was removed
@@ -524,34 +578,27 @@
    */
   SourceFactory _sourceFactory;
   /**
-   * A table mapping sources known to the context to the information known about the source.
+   * A table mapping the sources known to the context to the information known about the source.
    */
   Map<Source, SourceInfo> _sourceMap = new Map<Source, SourceInfo>();
   /**
-   * A cache mapping sources to the compilation units that were produced for the contents of the
+   * A table mapping sources to the change notices that are waiting to be returned related to that
    * source.
    */
-  Map<Source, CompilationUnit> _parseCache = new Map<Source, CompilationUnit>();
-  /**
-   * A cache mapping sources to the html parse results that were produced for the contents of the
-   * source.
-   */
-  Map<Source, HtmlParseResult> _htmlParseCache = new Map<Source, HtmlParseResult>();
-  /**
-   * A cache mapping sources (of the defining compilation units of libraries) to the library
-   * elements for those libraries.
-   */
-  Map<Source, LibraryElement> _libraryElementCache = new Map<Source, LibraryElement>();
-  /**
-   * A cache mapping sources (of the defining compilation units of libraries) to the public
-   * namespace for that library.
-   */
-  Map<Source, Namespace> _publicNamespaceCache = new Map<Source, Namespace>();
+  Map<Source, ChangeNoticeImpl> _pendingNotices = new Map<Source, ChangeNoticeImpl>();
   /**
    * The object used to synchronize access to all of the caches.
    */
   Object _cacheLock = new Object();
   /**
+   * The name of the 'src' attribute in a HTML tag.
+   */
+  static String _ATTRIBUTE_SRC = "src";
+  /**
+   * The name of the 'script' tag in an HTML file.
+   */
+  static String _TAG_SCRIPT = "script";
+  /**
    * Initialize a newly created analysis context.
    */
   AnalysisContextImpl() : super() {
@@ -561,26 +608,14 @@
       return;
     }
     {
-      List<Source> addedSources = new List<Source>();
-      for (MapEntry<Source, String> entry in getMapEntrySet(changeSet.addedWithContent)) {
-        Source source = entry.getKey();
-        _sourceFactory.setContents(source, entry.getValue());
-        addedSources.add(source);
-      }
-      List<Source> changedSources = new List<Source>();
-      for (MapEntry<Source, String> entry in getMapEntrySet(changeSet.changedWithContent)) {
-        Source source = entry.getKey();
-        _sourceFactory.setContents(source, entry.getValue());
-        changedSources.add(source);
-      }
       List<Source> removedSources = new List<Source>.from(changeSet.removed);
       for (SourceContainer container in changeSet.removedContainers) {
         addSourcesInContainer(removedSources, container);
       }
-      for (Source source in addedSources) {
+      for (Source source in changeSet.added3) {
         sourceAvailable(source);
       }
-      for (Source source in changedSources) {
+      for (Source source in changeSet.changed3) {
         sourceChanged(source);
       }
       for (Source source in removedSources) {
@@ -588,6 +623,106 @@
       }
     }
   }
+  List<AnalysisError> computeErrors(Source source) {
+    {
+      CompilationUnitInfo info = getCompilationUnitInfo(source);
+      if (info == null) {
+        return AnalysisError.NO_ERRORS;
+      }
+      if (info.hasInvalidParseErrors()) {
+        parseCompilationUnit(source);
+      }
+      if (info.hasInvalidResolutionErrors()) {
+      }
+      return info.allErrors;
+    }
+  }
+  HtmlElement computeHtmlElement(Source source) {
+    if (!AnalysisEngine.isHtmlFileName(source.shortName)) {
+      return null;
+    }
+    {
+      HtmlUnitInfo htmlUnitInfo = getHtmlUnitInfo(source);
+      if (htmlUnitInfo == null) {
+        return null;
+      }
+      HtmlElement element24 = htmlUnitInfo.element;
+      if (element24 == null) {
+        HtmlUnit unit = htmlUnitInfo.resolvedUnit;
+        if (unit == null) {
+          unit = htmlUnitInfo.parsedUnit;
+          if (unit == null) {
+            unit = parseHtmlUnit(source);
+          }
+        }
+        HtmlUnitBuilder builder = new HtmlUnitBuilder(this);
+        element24 = builder.buildHtmlElement2(source, unit);
+        htmlUnitInfo.resolvedUnit = unit;
+        htmlUnitInfo.element = element24;
+      }
+      return element24;
+    }
+  }
+  SourceKind computeKindOf(Source source) {
+    {
+      SourceInfo sourceInfo = getSourceInfo(source);
+      if (sourceInfo == null) {
+        return SourceKind.UNKNOWN;
+      } else if (sourceInfo is DartInfo) {
+        sourceInfo = internalComputeKindOf(source, sourceInfo);
+      }
+      return sourceInfo.kind;
+    }
+  }
+  LibraryElement computeLibraryElement(Source source) {
+    if (!AnalysisEngine.isDartFileName(source.shortName)) {
+      return null;
+    }
+    {
+      LibraryInfo libraryInfo = getLibraryInfo(source);
+      if (libraryInfo == null) {
+        return null;
+      }
+      LibraryElement element25 = libraryInfo.element;
+      if (element25 == null) {
+        if (computeKindOf(source) != SourceKind.LIBRARY) {
+          return null;
+        }
+        LibraryResolver resolver = new LibraryResolver.con1(this);
+        try {
+          element25 = resolver.resolveLibrary(source, true);
+          if (element25 != null) {
+            libraryInfo.element = element25;
+          }
+        } on AnalysisException catch (exception) {
+          AnalysisEngine.instance.logger.logError2("Could not resolve the library ${source.fullName}", exception);
+        }
+      }
+      return element25;
+    }
+  }
+  LineInfo computeLineInfo(Source source) {
+    {
+      SourceInfo sourceInfo = getSourceInfo(source);
+      if (sourceInfo == null) {
+        return null;
+      }
+      LineInfo lineInfo4 = sourceInfo.lineInfo;
+      if (lineInfo4 == null) {
+        if (sourceInfo is DartInfo) {
+          sourceInfo = internalComputeKindOf(source, sourceInfo);
+        }
+        if (sourceInfo is HtmlUnitInfo) {
+          parseHtmlUnit(source);
+          lineInfo4 = sourceInfo.lineInfo;
+        } else if (sourceInfo is CompilationUnitInfo) {
+          parseCompilationUnit(source);
+          lineInfo4 = sourceInfo.lineInfo;
+        }
+      }
+      return lineInfo4;
+    }
+  }
   AnalysisContext extractContext(SourceContainer container) {
     AnalysisContextImpl newContext = AnalysisEngine.instance.createAnalysisContext() as AnalysisContextImpl;
     List<Source> sourcesToRemove = new List<Source>();
@@ -596,95 +731,132 @@
         Source source = entry.getKey();
         if (container.contains(source)) {
           sourcesToRemove.add(source);
-          newContext._sourceMap[source] = new SourceInfo.con2(entry.getValue());
+          newContext._sourceMap[source] = entry.getValue().copy();
         }
       }
     }
     return newContext;
   }
   Element getElement(ElementLocation location) {
-    throw new UnsupportedOperationException();
+    List<String> components2 = ((location as ElementLocationImpl)).components;
+    ElementImpl element;
+    {
+      Source librarySource = _sourceFactory.fromEncoding(components2[0]);
+      try {
+        element = computeLibraryElement(librarySource) as ElementImpl;
+      } on AnalysisException catch (exception) {
+        return null;
+      }
+    }
+    for (int i = 1; i < components2.length; i++) {
+      if (element == null) {
+        return null;
+      }
+      element = element.getChild(components2[i]);
+    }
+    return element;
   }
   List<AnalysisError> getErrors(Source source) {
-    throw new UnsupportedOperationException();
+    {
+      SourceInfo info = getSourceInfo(source);
+      if (info is CompilationUnitInfo) {
+        return ((info as CompilationUnitInfo)).allErrors;
+      }
+      return AnalysisError.NO_ERRORS;
+    }
   }
   HtmlElement getHtmlElement(Source source) {
-    if (!AnalysisEngine.isHtmlFileName(source.shortName)) {
+    {
+      SourceInfo info = getSourceInfo(source);
+      if (info is HtmlUnitInfo) {
+        return ((info as HtmlUnitInfo)).element;
+      }
       return null;
     }
-    throw new UnsupportedOperationException();
+  }
+  List<Source> getHtmlFilesReferencing(Source source) {
+    {
+      SourceInfo info = getSourceInfo(source);
+      if (info is LibraryInfo) {
+        return ((info as LibraryInfo)).htmlSources;
+      } else if (info is CompilationUnitInfo) {
+        List<Source> sources = new List<Source>();
+        for (Source librarySource in ((info as CompilationUnitInfo)).librarySources) {
+          LibraryInfo libraryInfo = getLibraryInfo(librarySource);
+          for (Source htmlSource in libraryInfo.htmlSources) {
+            sources.add(htmlSource);
+          }
+        }
+        if (!sources.isEmpty) {
+          return new List.from(sources);
+        }
+      }
+      return Source.EMPTY_ARRAY;
+    }
   }
   List<Source> get htmlSources => getSources(SourceKind.HTML);
-  SourceKind getKnownKindOf(Source source) {
-    String name = source.shortName;
-    if (AnalysisEngine.isHtmlFileName(name)) {
-      return SourceKind.HTML;
-    }
-    if (!AnalysisEngine.isDartFileName(name)) {
-      return SourceKind.UNKNOWN;
-    }
+  SourceKind getKindOf(Source source) {
     {
-      if (_libraryElementCache.containsKey(source)) {
-        return SourceKind.LIBRARY;
+      SourceInfo sourceInfo = getSourceInfo(source);
+      if (sourceInfo == null) {
+        return SourceKind.UNKNOWN;
       }
-      CompilationUnit unit = _parseCache[source];
-      if (unit != null && hasPartOfDirective(unit)) {
-        return SourceKind.PART;
+      return sourceInfo.kind;
+    }
+  }
+  List<Source> get launchableClientLibrarySources {
+    List<Source> sources = new List<Source>();
+    {
+      for (MapEntry<Source, SourceInfo> entry in getMapEntrySet(_sourceMap)) {
+        Source source = entry.getKey();
+        SourceInfo info = entry.getValue();
+        if (identical(info.kind, SourceKind.LIBRARY) && !source.isInSystemLibrary()) {
+          sources.add(source);
+        }
       }
     }
-    return null;
+    return new List.from(sources);
   }
-  List<Source> get launchableClientLibrarySources => librarySources;
-  List<Source> get launchableServerLibrarySources => librarySources;
+  List<Source> get launchableServerLibrarySources {
+    List<Source> sources = new List<Source>();
+    {
+      for (MapEntry<Source, SourceInfo> entry in getMapEntrySet(_sourceMap)) {
+        Source source = entry.getKey();
+        SourceInfo info = entry.getValue();
+        if (identical(info.kind, SourceKind.LIBRARY) && !source.isInSystemLibrary()) {
+          sources.add(source);
+        }
+      }
+    }
+    return new List.from(sources);
+  }
   List<Source> getLibrariesContaining(Source source) {
     {
-      SourceInfo info = _sourceMap[source];
-      if (info == null) {
-        return Source.EMPTY_ARRAY;
+      SourceInfo info = getSourceInfo(source);
+      if (info is CompilationUnitInfo) {
+        return ((info as CompilationUnitInfo)).librarySources;
       }
-      return info.librarySources;
+      return Source.EMPTY_ARRAY;
     }
   }
   LibraryElement getLibraryElement(Source source) {
-    if (!AnalysisEngine.isDartFileName(source.shortName)) {
-      return null;
-    }
     {
-      LibraryElement element = _libraryElementCache[source];
-      if (element == null) {
-        if (getOrComputeKindOf(source) != SourceKind.LIBRARY) {
-          return null;
-        }
-        LibraryResolver resolver = new LibraryResolver.con1(this);
-        try {
-          element = resolver.resolveLibrary(source, true);
-          if (element != null) {
-            _libraryElementCache[source] = element;
-          }
-        } on AnalysisException catch (exception) {
-          AnalysisEngine.instance.logger.logError2("Could not resolve the library ${source.fullName}", exception);
-        }
+      SourceInfo info = getSourceInfo(source);
+      if (info is LibraryInfo) {
+        return ((info as LibraryInfo)).element;
       }
-      return element;
-    }
-  }
-  /**
-   * Return the element model corresponding to the library defined by the given source, or{@code null} if the element model does not yet exist.
-   * @param source the source defining the library whose element model is to be returned
-   * @return the element model corresponding to the library defined by the given source
-   */
-  LibraryElement getLibraryElementOrNull(Source source) {
-    {
-      return _libraryElementCache[source];
+      return null;
     }
   }
   List<Source> get librarySources => getSources(SourceKind.LIBRARY);
-  SourceKind getOrComputeKindOf(Source source) {
-    SourceKind kind = getKnownKindOf(source);
-    if (kind != null) {
-      return kind;
+  LineInfo getLineInfo(Source source) {
+    {
+      SourceInfo info = getSourceInfo(source);
+      if (info != null) {
+        return info.lineInfo;
+      }
+      return null;
     }
-    return computeKindOf(source);
   }
   /**
    * Return a namespace containing mappings for all of the public names defined by the given
@@ -693,13 +865,17 @@
    * @return the public namespace of the given library
    */
   Namespace getPublicNamespace(LibraryElement library) {
-    Source source10 = library.definingCompilationUnit.source;
+    Source source8 = library.definingCompilationUnit.source;
     {
-      Namespace namespace = _publicNamespaceCache[source10];
+      LibraryInfo libraryInfo = getLibraryInfo(source8);
+      if (libraryInfo == null) {
+        return null;
+      }
+      Namespace namespace = libraryInfo.publicNamespace;
       if (namespace == null) {
         NamespaceBuilder builder = new NamespaceBuilder();
         namespace = builder.createPublicNamespace(library);
-        _publicNamespaceCache[source10] = namespace;
+        libraryInfo.publicNamespace = namespace;
       }
       return namespace;
     }
@@ -709,74 +885,131 @@
    * defined by the given source.
    * @param source the source defining the library whose public namespace is to be returned
    * @return the public namespace corresponding to the library defined by the given source
+   * @throws AnalysisException if the public namespace could not be computed
    */
   Namespace getPublicNamespace2(Source source) {
     {
-      Namespace namespace = _publicNamespaceCache[source];
+      LibraryInfo libraryInfo = getLibraryInfo(source);
+      if (libraryInfo == null) {
+        return null;
+      }
+      Namespace namespace = libraryInfo.publicNamespace;
       if (namespace == null) {
-        LibraryElement library = getLibraryElement(source);
+        LibraryElement library = computeLibraryElement(source);
         if (library == null) {
           return null;
         }
         NamespaceBuilder builder = new NamespaceBuilder();
         namespace = builder.createPublicNamespace(library);
-        _publicNamespaceCache[source] = namespace;
+        libraryInfo.publicNamespace = namespace;
       }
       return namespace;
     }
   }
   SourceFactory get sourceFactory => _sourceFactory;
+  bool isClientLibrary(Source librarySource) {
+    SourceInfo sourceInfo = getSourceInfo(librarySource);
+    if (sourceInfo is LibraryInfo) {
+      LibraryInfo libraryInfo = sourceInfo as LibraryInfo;
+      if (libraryInfo.hasInvalidLaunchable() || libraryInfo.hasInvalidClientServer()) {
+        return false;
+      }
+      return libraryInfo.isLaunchable() && libraryInfo.isClient();
+    }
+    return false;
+  }
+  bool isServerLibrary(Source librarySource) {
+    SourceInfo sourceInfo = getSourceInfo(librarySource);
+    if (sourceInfo is LibraryInfo) {
+      LibraryInfo libraryInfo = sourceInfo as LibraryInfo;
+      if (libraryInfo.hasInvalidLaunchable() || libraryInfo.hasInvalidClientServer()) {
+        return false;
+      }
+      return libraryInfo.isLaunchable() && libraryInfo.isServer();
+    }
+    return false;
+  }
   void mergeContext(AnalysisContext context) {
     {
       for (MapEntry<Source, SourceInfo> entry in getMapEntrySet(((context as AnalysisContextImpl))._sourceMap)) {
         Source newSource = entry.getKey();
-        SourceInfo existingInfo = _sourceMap[newSource];
+        SourceInfo existingInfo = getSourceInfo(newSource);
         if (existingInfo == null) {
-          _sourceMap[newSource] = new SourceInfo.con2(entry.getValue());
+          _sourceMap[newSource] = entry.getValue().copy();
         } else {
         }
       }
     }
   }
-  CompilationUnit parse(Source source) {
+  CompilationUnit parseCompilationUnit(Source source) {
     {
-      CompilationUnit unit = _parseCache[source];
+      CompilationUnitInfo compilationUnitInfo = getCompilationUnitInfo(source);
+      if (compilationUnitInfo == null) {
+        return null;
+      }
+      CompilationUnit unit = compilationUnitInfo.resolvedCompilationUnit;
       if (unit == null) {
-        RecordingErrorListener errorListener = new RecordingErrorListener();
-        AnalysisContextImpl_ScanResult scanResult = internalScan(source, errorListener);
-        Parser parser = new Parser(source, errorListener);
-        unit = parser.parseCompilationUnit(scanResult._token);
-        unit.parsingErrors = errorListener.getErrors2(source);
-        unit.lineInfo = new LineInfo(scanResult._lineStarts);
-        _parseCache[source] = unit;
+        unit = compilationUnitInfo.parsedCompilationUnit;
+        if (unit == null) {
+          RecordingErrorListener errorListener = new RecordingErrorListener();
+          AnalysisContextImpl_ScanResult scanResult = internalScan(source, errorListener);
+          Parser parser = new Parser(source, errorListener);
+          unit = parser.parseCompilationUnit(scanResult._token);
+          LineInfo lineInfo = new LineInfo(scanResult._lineStarts);
+          List<AnalysisError> errors = errorListener.getErrors2(source);
+          unit.parsingErrors = errors;
+          unit.lineInfo = lineInfo;
+          compilationUnitInfo.lineInfo = lineInfo;
+          compilationUnitInfo.parsedCompilationUnit = unit;
+          compilationUnitInfo.parseErrors = errors;
+        }
       }
       return unit;
     }
   }
-  CompilationUnit parse3(Source source, AnalysisErrorListener errorListener) {
+  HtmlUnit parseHtmlUnit(Source source) {
     {
-      CompilationUnit unit = _parseCache[source];
+      HtmlUnitInfo htmlUnitInfo = getHtmlUnitInfo(source);
+      if (htmlUnitInfo == null) {
+        return null;
+      }
+      HtmlUnit unit = htmlUnitInfo.resolvedUnit;
       if (unit == null) {
-        AnalysisContextImpl_ScanResult scanResult = internalScan(source, errorListener);
-        Parser parser = new Parser(source, errorListener);
-        unit = parser.parseCompilationUnit(scanResult._token);
-        unit.lineInfo = new LineInfo(scanResult._lineStarts);
-        _parseCache[source] = unit;
+        unit = htmlUnitInfo.parsedUnit;
+        if (unit == null) {
+          HtmlParseResult result = new HtmlParser(source).parse(scanHtml(source));
+          unit = result.htmlUnit;
+          htmlUnitInfo.lineInfo = new LineInfo(result.lineStarts);
+          htmlUnitInfo.parsedUnit = unit;
+          for (SourceInfo sourceInfo in _sourceMap.values) {
+            if (sourceInfo is LibraryInfo) {
+              ((sourceInfo as LibraryInfo)).removeHtmlSource(source);
+            }
+          }
+          for (Source librarySource in getLibrarySources2(source, unit)) {
+            LibraryInfo libraryInfo = getLibraryInfo(librarySource);
+            if (libraryInfo != null) {
+              libraryInfo.addHtmlSource(source);
+            }
+          }
+        }
       }
       return unit;
     }
   }
-  HtmlParseResult parseHtml(Source source) {
+  List<ChangeNotice> performAnalysisTask() {
     {
-      HtmlParseResult result = _htmlParseCache[source];
-      if (result == null) {
-        result = new HtmlParser(source).parse(scanHtml(source));
-        _htmlParseCache[source] = result;
+      if (!performSingleAnalysisTask() && _pendingNotices.isEmpty) {
+        return null;
       }
-      return result;
+      if (_pendingNotices.isEmpty) {
+        return ChangeNoticeImpl.EMPTY_ARRAY;
+      }
+      List<ChangeNotice> notices = new List.from(_pendingNotices.values);
+      _pendingNotices.clear();
+      return notices;
     }
   }
-  List<ChangeNotice> performAnalysisTask() => ChangeNotice.EMPTY_ARRAY;
   /**
    * Given a table mapping the source for the libraries represented by the corresponding elements to
    * the elements representing the libraries, record those mappings.
@@ -784,26 +1017,142 @@
    * the elements representing the libraries
    */
   void recordLibraryElements(Map<Source, LibraryElement> elementMap) {
+    Source htmlSource = _sourceFactory.forUri("dart:html");
     {
-      javaMapPutAll(_libraryElementCache, elementMap);
+      for (MapEntry<Source, LibraryElement> entry in getMapEntrySet(elementMap)) {
+        LibraryElement library = entry.getValue();
+        LibraryInfo libraryInfo = getLibraryInfo(entry.getKey());
+        if (libraryInfo != null) {
+          libraryInfo.element = library;
+          libraryInfo.launchable = library.entryPoint != null;
+          libraryInfo.client = isClient(library, htmlSource, new Set<LibraryElement>());
+        }
+        Source librarySource = library.source;
+        if (librarySource != null) {
+          for (SourceInfo info in _sourceMap.values) {
+            if (info is CompilationUnitInfo) {
+              ((info as CompilationUnitInfo)).removeLibrarySource(librarySource);
+            }
+          }
+          if (libraryInfo != null) {
+            libraryInfo.addLibrarySource(librarySource);
+          }
+          for (CompilationUnitElement part in library.parts) {
+            Source partSource = part.source;
+            CompilationUnitInfo partInfo = partSource == null ? null : getCompilationUnitInfo(partSource);
+            if (partInfo != null) {
+              partInfo.addLibrarySource(librarySource);
+            }
+          }
+        }
+      }
     }
   }
-  CompilationUnit resolve(Source source, LibraryElement library) => parse(source);
+  /**
+   * Give the resolution errors and line info associated with the given source, add the information
+   * to the cache.
+   * @param source the source with which the information is associated
+   * @param errors the resolution errors associated with the source
+   * @param lineInfo the line information associated with the source
+   */
+  void recordResolutionErrors(Source source, List<AnalysisError> errors, LineInfo lineInfo5) {
+    {
+      CompilationUnitInfo compilationUnitInfo = getCompilationUnitInfo(source);
+      if (compilationUnitInfo != null) {
+        compilationUnitInfo.lineInfo = lineInfo5;
+        compilationUnitInfo.resolutionErrors = errors;
+      }
+      getNotice(source).setErrors(compilationUnitInfo.allErrors, lineInfo5);
+    }
+  }
+  /**
+   * Give the resolved compilation unit associated with the given source, add the unit to the cache.
+   * @param source the source with which the unit is associated
+   * @param unit the compilation unit associated with the source
+   */
+  void recordResolvedCompilationUnit(Source source, CompilationUnit unit) {
+    {
+      CompilationUnitInfo compilationUnitInfo = getCompilationUnitInfo(source);
+      if (compilationUnitInfo != null) {
+        compilationUnitInfo.resolvedCompilationUnit = unit;
+        getNotice(source).compilationUnit = unit;
+      }
+    }
+  }
+  CompilationUnit resolveCompilationUnit(Source source15, LibraryElement library) {
+    if (library == null) {
+      return null;
+    }
+    return resolveCompilationUnit2(source15, library.source);
+  }
+  CompilationUnit resolveCompilationUnit2(Source unitSource, Source librarySource) {
+    {
+      CompilationUnitInfo compilationUnitInfo = getCompilationUnitInfo(unitSource);
+      if (compilationUnitInfo == null) {
+        return null;
+      }
+      CompilationUnit unit = compilationUnitInfo.resolvedCompilationUnit;
+      if (unit == null) {
+        computeLibraryElement(librarySource);
+        unit = compilationUnitInfo.resolvedCompilationUnit;
+      }
+      return unit;
+    }
+  }
+  HtmlUnit resolveHtmlUnit(Source unitSource) {
+    {
+      HtmlUnitInfo htmlUnitInfo = getHtmlUnitInfo(unitSource);
+      if (htmlUnitInfo == null) {
+        return null;
+      }
+      HtmlUnit unit = htmlUnitInfo.resolvedUnit;
+      if (unit == null) {
+        computeHtmlElement(unitSource);
+        unit = htmlUnitInfo.resolvedUnit;
+      }
+      return unit;
+    }
+  }
+  void setContents(Source source, String contents) {
+    {
+      _sourceFactory.setContents(source, contents);
+      sourceChanged(source);
+    }
+  }
   void set sourceFactory(SourceFactory factory) {
     if (identical(_sourceFactory, factory)) {
       return;
     } else if (factory.context != null) {
       throw new IllegalStateException("Source factories cannot be shared between contexts");
-    } else if (_sourceFactory != null) {
-      _sourceFactory.context = null;
     }
-    factory.context = this;
-    _sourceFactory = factory;
+    {
+      if (_sourceFactory != null) {
+        _sourceFactory.context = null;
+      }
+      factory.context = this;
+      _sourceFactory = factory;
+      for (SourceInfo sourceInfo in _sourceMap.values) {
+        if (sourceInfo is HtmlUnitInfo) {
+          ((sourceInfo as HtmlUnitInfo)).invalidateResolvedUnit();
+        } else if (sourceInfo is CompilationUnitInfo) {
+          CompilationUnitInfo compilationUnitInfo = sourceInfo as CompilationUnitInfo;
+          compilationUnitInfo.invalidateResolvedUnit();
+          compilationUnitInfo.invalidateResolutionErrors();
+          if (sourceInfo is LibraryInfo) {
+            LibraryInfo libraryInfo = sourceInfo as LibraryInfo;
+            libraryInfo.invalidateElement();
+            libraryInfo.invalidatePublicNamespace();
+            libraryInfo.invalidateLaunchable();
+            libraryInfo.invalidateClientServer();
+          }
+        }
+      }
+    }
   }
   Iterable<Source> sourcesToResolve(List<Source> changedSources) {
     List<Source> librarySources = new List<Source>();
     for (Source source in changedSources) {
-      if (identical(getOrComputeKindOf(source), SourceKind.LIBRARY)) {
+      if (identical(computeKindOf(source), SourceKind.LIBRARY)) {
         librarySources.add(source);
       }
     }
@@ -823,26 +1172,151 @@
       }
     }
   }
-  SourceKind computeKindOf(Source source) {
-    try {
-      if (hasPartOfDirective(parse(source))) {
-        return SourceKind.PART;
-      }
-    } on AnalysisException catch (exception) {
-      return SourceKind.UNKNOWN;
+  /**
+   * Create a source information object suitable for the given source. Return the source information
+   * object that was created, or {@code null} if the source should not be tracked by this context.
+   * @param source the source for which an information object is being created
+   * @return the source information object that was created
+   */
+  SourceInfo createSourceInfo(Source source) {
+    String name = source.shortName;
+    if (AnalysisEngine.isHtmlFileName(name)) {
+      HtmlUnitInfo info = new HtmlUnitInfo();
+      _sourceMap[source] = info;
+      return info;
+    } else if (AnalysisEngine.isDartFileName(name)) {
+      DartInfo info = DartInfo.instance;
+      _sourceMap[source] = info;
+      return info;
     }
-    return SourceKind.LIBRARY;
+    return null;
+  }
+  /**
+   * Return the compilation unit information associated with the given source, or {@code null} if
+   * the source is not known to this context. This method should be used to access the compilation
+   * unit information rather than accessing the compilation unit map directly because sources in the
+   * SDK are implicitly part of every analysis context and are therefore only added to the map when
+   * first accessed.
+   * <p>
+   * <b>Note:</b> This method must only be invoked while we are synchronized on {@link #cacheLock}.
+   * @param source the source for which information is being sought
+   * @return the compilation unit information associated with the given source
+   */
+  CompilationUnitInfo getCompilationUnitInfo(Source source) {
+    SourceInfo sourceInfo = getSourceInfo(source);
+    if (sourceInfo == null) {
+      sourceInfo = new CompilationUnitInfo();
+      _sourceMap[source] = sourceInfo;
+      return sourceInfo as CompilationUnitInfo;
+    } else if (sourceInfo is CompilationUnitInfo) {
+      return sourceInfo as CompilationUnitInfo;
+    } else if (sourceInfo is DartInfo) {
+      sourceInfo = internalComputeKindOf(source, sourceInfo);
+      if (sourceInfo is CompilationUnitInfo) {
+        return sourceInfo as CompilationUnitInfo;
+      }
+    }
+    return null;
+  }
+  /**
+   * Return the HTML unit information associated with the given source, or {@code null} if the
+   * source is not known to this context. This method should be used to access the HTML unit
+   * information rather than accessing the HTML unit map directly because sources in the SDK are
+   * implicitly part of every analysis context and are therefore only added to the map when first
+   * accessed.
+   * <p>
+   * <b>Note:</b> This method must only be invoked while we are synchronized on {@link #cacheLock}.
+   * @param source the source for which information is being sought
+   * @return the HTML unit information associated with the given source
+   */
+  HtmlUnitInfo getHtmlUnitInfo(Source source) {
+    SourceInfo sourceInfo = getSourceInfo(source);
+    if (sourceInfo == null) {
+      sourceInfo = new HtmlUnitInfo();
+      _sourceMap[source] = sourceInfo;
+      return sourceInfo as HtmlUnitInfo;
+    } else if (sourceInfo is HtmlUnitInfo) {
+      return sourceInfo as HtmlUnitInfo;
+    }
+    return null;
+  }
+  /**
+   * Return the library information associated with the given source, or {@code null} if the source
+   * is not known to this context. This method should be used to access the library information
+   * rather than accessing the library map directly because sources in the SDK are implicitly part
+   * of every analysis context and are therefore only added to the map when first accessed.
+   * <p>
+   * <b>Note:</b> This method must only be invoked while we are synchronized on {@link #cacheLock}.
+   * @param source the source for which information is being sought
+   * @return the library information associated with the given source
+   */
+  LibraryInfo getLibraryInfo(Source source) {
+    SourceInfo sourceInfo = getSourceInfo(source);
+    if (sourceInfo == null) {
+      sourceInfo = new LibraryInfo();
+      _sourceMap[source] = sourceInfo;
+      return sourceInfo as LibraryInfo;
+    } else if (sourceInfo is LibraryInfo) {
+      return sourceInfo as LibraryInfo;
+    } else if (sourceInfo is DartInfo) {
+      sourceInfo = internalComputeKindOf(source, sourceInfo);
+      if (sourceInfo is LibraryInfo) {
+        return sourceInfo as LibraryInfo;
+      }
+    }
+    return null;
+  }
+  /**
+   * Return the sources of libraries that are referenced in the specified HTML file.
+   * @param htmlSource the source of the HTML file being analyzed
+   * @param htmlUnit the AST for the HTML file being analyzed
+   * @return the sources of libraries that are referenced in the HTML file
+   */
+  List<Source> getLibrarySources2(Source htmlSource, HtmlUnit htmlUnit) {
+    List<Source> libraries = new List<Source>();
+    htmlUnit.accept(new SimpleXmlVisitor_3(htmlSource, libraries));
+    return libraries;
+  }
+  /**
+   * Return a change notice for the given source, creating one if one does not already exist.
+   * @param source the source for which changes are being reported
+   * @return a change notice for the given source
+   */
+  ChangeNoticeImpl getNotice(Source source) {
+    ChangeNoticeImpl notice = _pendingNotices[source];
+    if (notice == null) {
+      notice = new ChangeNoticeImpl(source);
+      _pendingNotices[source] = notice;
+    }
+    return notice;
+  }
+  /**
+   * Return the source information associated with the given source, or {@code null} if the source
+   * is not known to this context. This method should be used to access the source information
+   * rather than accessing the source map directly because sources in the SDK are implicitly part of
+   * every analysis context and are therefore only added to the map when first accessed.
+   * <p>
+   * <b>Note:</b> This method must only be invoked while we are synchronized on {@link #cacheLock}.
+   * @param source the source for which information is being sought
+   * @return the source information associated with the given source
+   */
+  SourceInfo getSourceInfo(Source source) {
+    SourceInfo sourceInfo = _sourceMap[source];
+    if (sourceInfo == null) {
+      sourceInfo = createSourceInfo(source);
+    }
+    return sourceInfo;
   }
   /**
    * Return an array containing all of the sources known to this context that have the given kind.
    * @param kind the kind of sources to be returned
    * @return all of the sources known to this context that have the given kind
    */
-  List<Source> getSources(SourceKind kind5) {
+  List<Source> getSources(SourceKind kind3) {
     List<Source> sources = new List<Source>();
     {
       for (MapEntry<Source, SourceInfo> entry in getMapEntrySet(_sourceMap)) {
-        if (identical(entry.getValue().kind, kind5)) {
+        if (identical(entry.getValue().kind, kind3)) {
           sources.add(entry.getKey());
         }
       }
@@ -862,74 +1336,185 @@
     }
     return false;
   }
+  SourceInfo internalComputeKindOf(Source source, SourceInfo info) {
+    try {
+      RecordingErrorListener errorListener = new RecordingErrorListener();
+      AnalysisContextImpl_ScanResult scanResult = internalScan(source, errorListener);
+      Parser parser = new Parser(source, errorListener);
+      CompilationUnit unit = parser.parseCompilationUnit(scanResult._token);
+      LineInfo lineInfo = new LineInfo(scanResult._lineStarts);
+      List<AnalysisError> errors = errorListener.getErrors2(source);
+      unit.parsingErrors = errors;
+      unit.lineInfo = lineInfo;
+      CompilationUnitInfo sourceInfo;
+      if (hasPartOfDirective(unit)) {
+        sourceInfo = new CompilationUnitInfo();
+      } else {
+        sourceInfo = new LibraryInfo();
+      }
+      sourceInfo.lineInfo = lineInfo;
+      sourceInfo.parsedCompilationUnit = unit;
+      sourceInfo.parseErrors = errors;
+      _sourceMap[source] = sourceInfo;
+      return sourceInfo;
+    } on AnalysisException catch (exception) {
+      return info;
+    }
+  }
   AnalysisContextImpl_ScanResult internalScan(Source source, AnalysisErrorListener errorListener) {
     AnalysisContextImpl_ScanResult result = new AnalysisContextImpl_ScanResult();
-    Source_ContentReceiver receiver = new Source_ContentReceiver_3(source, errorListener, result);
+    Source_ContentReceiver receiver = new Source_ContentReceiver_4(source, errorListener, result);
     try {
       source.getContents(receiver);
-    } on JavaException catch (exception) {
+    } catch (exception) {
       throw new AnalysisException.con3(exception);
     }
     return result;
   }
+  /**
+   * Return {@code true} if this library is, or depends on, dart:html.
+   * @param library the library being tested
+   * @param visitedLibraries a collection of the libraries that have been visited, used to prevent
+   * infinite recursion
+   * @return {@code true} if this library is, or depends on, dart:html
+   */
+  bool isClient(LibraryElement library, Source htmlSource, Set<LibraryElement> visitedLibraries) {
+    if (visitedLibraries.contains(library)) {
+      return false;
+    }
+    if (library.source == htmlSource) {
+      return true;
+    }
+    javaSetAdd(visitedLibraries, library);
+    for (LibraryElement imported in library.importedLibraries) {
+      if (isClient(imported, htmlSource, visitedLibraries)) {
+        return true;
+      }
+    }
+    for (LibraryElement exported in library.exportedLibraries) {
+      if (isClient(exported, htmlSource, visitedLibraries)) {
+        return true;
+      }
+    }
+    return false;
+  }
+  /**
+   * Perform a single analysis task.
+   * <p>
+   * <b>Note:</b> This method must only be invoked while we are synchronized on {@link #cacheLock}.
+   * @return {@code true} if work was done, implying that there might be more work to be done
+   */
+  bool performSingleAnalysisTask() {
+    for (MapEntry<Source, SourceInfo> entry in getMapEntrySet(_sourceMap)) {
+      SourceInfo sourceInfo = entry.getValue();
+      if (identical(sourceInfo, DartInfo.instance) || sourceInfo.kind == null) {
+        internalComputeKindOf(entry.getKey(), sourceInfo);
+        return true;
+      }
+    }
+    for (MapEntry<Source, SourceInfo> entry in getMapEntrySet(_sourceMap)) {
+      SourceInfo sourceInfo = entry.getValue();
+      if (sourceInfo is CompilationUnitInfo) {
+        CompilationUnitInfo unitInfo = sourceInfo as CompilationUnitInfo;
+        if (unitInfo.hasInvalidParsedUnit()) {
+          try {
+            parseCompilationUnit(entry.getKey());
+          } on AnalysisException catch (exception) {
+            unitInfo.parsedCompilationUnit = null;
+            AnalysisEngine.instance.logger.logError2("Could not parse ${entry.getKey().fullName}", exception);
+          }
+          return true;
+        }
+      } else if (sourceInfo is HtmlUnitInfo) {
+        HtmlUnitInfo unitInfo = sourceInfo as HtmlUnitInfo;
+        if (unitInfo.hasInvalidParsedUnit()) {
+          try {
+            parseHtmlUnit(entry.getKey());
+          } on AnalysisException catch (exception) {
+            unitInfo.parsedUnit = null;
+            AnalysisEngine.instance.logger.logError2("Could not parse ${entry.getKey().fullName}", exception);
+          }
+          return true;
+        }
+      }
+    }
+    for (MapEntry<Source, SourceInfo> entry in getMapEntrySet(_sourceMap)) {
+      SourceInfo sourceInfo = entry.getValue();
+      if (sourceInfo is LibraryInfo) {
+        LibraryInfo libraryInfo = sourceInfo as LibraryInfo;
+        if (libraryInfo.hasInvalidElement()) {
+          try {
+            computeLibraryElement(entry.getKey());
+          } on AnalysisException catch (exception) {
+            libraryInfo.element = null;
+            AnalysisEngine.instance.logger.logError2("Could not compute the library element for ${entry.getKey().fullName}", exception);
+          }
+          return true;
+        }
+      }
+    }
+    return false;
+  }
   HtmlScanResult scanHtml(Source source) {
     HtmlScanner scanner = new HtmlScanner(source);
     try {
       source.getContents(scanner);
-    } on JavaException catch (exception) {
+    } catch (exception) {
       throw new AnalysisException.con3(exception);
     }
     return scanner.result;
   }
   /**
-   * Note: This method must only be invoked while we are synchronized on {@link #cacheLock}.
+   * <b>Note:</b> This method must only be invoked while we are synchronized on {@link #cacheLock}.
    * @param source the source that has been added
    */
   void sourceAvailable(Source source) {
     SourceInfo existingInfo = _sourceMap[source];
     if (existingInfo == null) {
-      SourceKind kind = computeKindOf(source);
-      _sourceMap[source] = new SourceInfo.con1(source, kind);
+      createSourceInfo(source);
     }
   }
   /**
-   * Note: This method must only be invoked while we are synchronized on {@link #cacheLock}.
+   * <b>Note:</b> This method must only be invoked while we are synchronized on {@link #cacheLock}.
    * @param source the source that has been changed
    */
   void sourceChanged(Source source) {
-    SourceInfo info = _sourceMap[source];
-    if (info == null) {
-      return;
-    }
-    _parseCache.remove(source);
-    _htmlParseCache.remove(source);
-    _libraryElementCache.remove(source);
-    _publicNamespaceCache.remove(source);
-    SourceKind oldKind = info.kind;
-    SourceKind newKind = computeKindOf(source);
-    if (newKind != oldKind) {
-      info.kind = newKind;
-    }
-    for (Source librarySource in info.librarySources) {
-      _libraryElementCache.remove(librarySource);
-      _publicNamespaceCache.remove(librarySource);
+    SourceInfo sourceInfo = _sourceMap[source];
+    if (sourceInfo is HtmlUnitInfo) {
+      HtmlUnitInfo htmlUnitInfo = sourceInfo as HtmlUnitInfo;
+      htmlUnitInfo.invalidateLineInfo();
+      htmlUnitInfo.invalidateParsedUnit();
+      htmlUnitInfo.invalidateResolvedUnit();
+    } else if (sourceInfo is CompilationUnitInfo) {
+      CompilationUnitInfo compilationUnitInfo = sourceInfo as CompilationUnitInfo;
+      for (Source librarySource in compilationUnitInfo.librarySources) {
+        LibraryInfo libraryInfo = getLibraryInfo(librarySource);
+        if (libraryInfo != null) {
+          libraryInfo.invalidateElement();
+          libraryInfo.invalidatePublicNamespace();
+          libraryInfo.invalidateLaunchable();
+          libraryInfo.invalidateClientServer();
+        }
+      }
+      _sourceMap[source] = DartInfo.instance;
     }
   }
   /**
-   * Note: This method must only be invoked while we are synchronized on {@link #cacheLock}.
+   * <b>Note:</b> This method must only be invoked while we are synchronized on {@link #cacheLock}.
    * @param source the source that has been deleted
    */
   void sourceRemoved(Source source) {
-    SourceInfo info = _sourceMap[source];
-    if (info == null) {
-      return;
-    }
-    _parseCache.remove(source);
-    _libraryElementCache.remove(source);
-    _publicNamespaceCache.remove(source);
-    for (Source librarySource in info.librarySources) {
-      _libraryElementCache.remove(librarySource);
-      _publicNamespaceCache.remove(librarySource);
+    CompilationUnitInfo compilationUnitInfo = getCompilationUnitInfo(source);
+    if (compilationUnitInfo != null) {
+      for (Source librarySource in compilationUnitInfo.librarySources) {
+        LibraryInfo libraryInfo = getLibraryInfo(librarySource);
+        if (libraryInfo != null) {
+          libraryInfo.invalidateElement();
+          libraryInfo.invalidatePublicNamespace();
+          libraryInfo.invalidateLaunchable();
+          libraryInfo.invalidateClientServer();
+        }
+      }
     }
     _sourceMap.remove(source);
   }
@@ -952,11 +1537,29 @@
   AnalysisContextImpl_ScanResult() : super() {
   }
 }
-class Source_ContentReceiver_3 implements Source_ContentReceiver {
+class SimpleXmlVisitor_3 extends SimpleXmlVisitor<Object> {
+  Source htmlSource;
+  List<Source> libraries;
+  SimpleXmlVisitor_3(this.htmlSource, this.libraries) : super();
+  Object visitXmlTagNode(XmlTagNode node) {
+    if (javaStringEqualsIgnoreCase(node.tag.lexeme, AnalysisContextImpl._TAG_SCRIPT)) {
+      for (XmlAttributeNode attribute in node.attributes) {
+        if (javaStringEqualsIgnoreCase(attribute.name.lexeme, AnalysisContextImpl._ATTRIBUTE_SRC)) {
+          Source librarySource = htmlSource.resolve(attribute.value.lexeme);
+          if (librarySource.exists()) {
+            libraries.add(librarySource);
+          }
+        }
+      }
+    }
+    return null;
+  }
+}
+class Source_ContentReceiver_4 implements Source_ContentReceiver {
   Source source;
   AnalysisErrorListener errorListener;
   AnalysisContextImpl_ScanResult result;
-  Source_ContentReceiver_3(this.source, this.errorListener, this.result);
+  Source_ContentReceiver_4(this.source, this.errorListener, this.result);
   accept(CharBuffer contents) {
     CharBufferScanner scanner = new CharBufferScanner(source, contents, errorListener);
     result._token = scanner.tokenize();
@@ -969,6 +1572,758 @@
   }
 }
 /**
+ * The enumeration {@code CacheState} defines the possible states of cached data.
+ */
+class CacheState {
+  /**
+   * A state representing the fact that the data was up-to-date but flushed from the cache in order
+   * to control memory usage.
+   */
+  static final CacheState FLUSHED = new CacheState('FLUSHED', 0);
+  /**
+   * A state representing the fact that the data was removed from the cache because it was invalid
+   * and needs to be recomputed.
+   */
+  static final CacheState INVALID = new CacheState('INVALID', 1);
+  /**
+   * A state representing the fact that the data is in the cache and valid.
+   */
+  static final CacheState VALID = new CacheState('VALID', 2);
+  static final List<CacheState> values = [FLUSHED, INVALID, VALID];
+  final String __name;
+  final int __ordinal;
+  int get ordinal => __ordinal;
+  CacheState(this.__name, this.__ordinal) {
+  }
+  String toString() => __name;
+}
+/**
+ * Instances of the class {@code ChangeNoticeImpl} represent a change to the analysis results
+ * associated with a given source.
+ * @coverage dart.engine
+ */
+class ChangeNoticeImpl implements ChangeNotice {
+  /**
+   * The source for which the result is being reported.
+   */
+  Source _source;
+  /**
+   * The fully resolved AST that changed as a result of the analysis, or {@code null} if the AST was
+   * not changed.
+   */
+  CompilationUnit _compilationUnit;
+  /**
+   * The errors that changed as a result of the analysis, or {@code null} if errors were not
+   * changed.
+   */
+  List<AnalysisError> _errors;
+  /**
+   * The line information associated with the source, or {@code null} if errors were not changed.
+   */
+  LineInfo _lineInfo;
+  /**
+   * An empty array of change notices.
+   */
+  static List<ChangeNoticeImpl> EMPTY_ARRAY = new List<ChangeNoticeImpl>(0);
+  /**
+   * Initialize a newly created notice associated with the given source.
+   * @param source the source for which the change is being reported
+   */
+  ChangeNoticeImpl(Source source) {
+    this._source = source;
+  }
+  /**
+   * Return the fully resolved AST that changed as a result of the analysis, or {@code null} if the
+   * AST was not changed.
+   * @return the fully resolved AST that changed as a result of the analysis
+   */
+  CompilationUnit get compilationUnit => _compilationUnit;
+  /**
+   * Return the errors that changed as a result of the analysis, or {@code null} if errors were not
+   * changed.
+   * @return the errors that changed as a result of the analysis
+   */
+  List<AnalysisError> get errors => _errors;
+  /**
+   * Return the line information associated with the source, or {@code null} if errors were not
+   * changed.
+   * @return the line information associated with the source
+   */
+  LineInfo get lineInfo => _lineInfo;
+  /**
+   * Return the source for which the result is being reported.
+   * @return the source for which the result is being reported
+   */
+  Source get source => _source;
+  /**
+   * Set the fully resolved AST that changed as a result of the analysis to the given AST.
+   * @param compilationUnit the fully resolved AST that changed as a result of the analysis
+   */
+  void set compilationUnit(CompilationUnit compilationUnit9) {
+    this._compilationUnit = compilationUnit9;
+  }
+  /**
+   * Set the errors that changed as a result of the analysis to the given errors and set the line
+   * information to the given line information.
+   * @param errors the errors that changed as a result of the analysis
+   * @param lineInfo the line information associated with the source
+   */
+  void setErrors(List<AnalysisError> errors2, LineInfo lineInfo3) {
+    this._errors = errors2;
+    this._lineInfo = lineInfo3;
+  }
+}
+/**
+ * Instances of the class {@code CompilationUnitInfo} maintain the information cached by an analysis
+ * context about an individual compilation unit.
+ * @coverage dart.engine
+ */
+class CompilationUnitInfo extends SourceInfo {
+  /**
+   * The state of the cached parsed compilation unit.
+   */
+  CacheState _parsedUnitState = CacheState.INVALID;
+  /**
+   * The parsed compilation unit, or {@code null} if the parsed compilation unit is not currently
+   * cached.
+   */
+  CompilationUnit _parsedUnit;
+  /**
+   * The state of the cached resolved compilation unit.
+   */
+  CacheState _resolvedUnitState = CacheState.INVALID;
+  /**
+   * The resolved compilation unit, or {@code null} if the resolved compilation unit is not
+   * currently cached.
+   */
+  CompilationUnit _resolvedUnit;
+  /**
+   * The state of the cached parse errors.
+   */
+  CacheState _parseErrorsState = CacheState.INVALID;
+  /**
+   * The errors produced while scanning and parsing the compilation unit, or {@code null} if the
+   * errors are not currently cached.
+   */
+  List<AnalysisError> _parseErrors;
+  /**
+   * The state of the cached resolution errors.
+   */
+  CacheState _resolutionErrorsState = CacheState.INVALID;
+  /**
+   * The errors produced while resolving the compilation unit, or {@code null} if the errors are not
+   * currently cached.
+   */
+  List<AnalysisError> _resolutionErrors;
+  /**
+   * The sources for the defining compilation units of the libraries containing the source, or{@code null} if the libraries containing the source are not yet known.
+   */
+  List<Source> _librarySources = null;
+  /**
+   * Initialize a newly created information holder to be empty.
+   */
+  CompilationUnitInfo() : super() {
+  }
+  /**
+   * Add the given source to the list of sources for the defining compilation units for the
+   * libraries containing this source.
+   * @param source the source to be added to the list
+   */
+  void addLibrarySource(Source source) {
+    if (_librarySources == null) {
+      _librarySources = new List<Source>();
+    }
+    _librarySources.add(source);
+  }
+  /**
+   * Remove the parsed compilation unit from the cache.
+   */
+  void clearParsedUnit() {
+    _parsedUnit = null;
+  }
+  /**
+   * Remove the parse errors from the cache.
+   */
+  void clearParseErrors() {
+    _parseErrors = null;
+  }
+  /**
+   * Remove the resolution errors from the cache.
+   */
+  void clearResolutionErrors() {
+    _resolutionErrors = null;
+  }
+  /**
+   * Remove the resolved compilation unit from the cache.
+   */
+  void clearResolvedUnit() {
+    _resolvedUnit = null;
+  }
+  CompilationUnitInfo copy() {
+    CompilationUnitInfo copy = new CompilationUnitInfo();
+    copy.copyFrom(this);
+    return copy;
+  }
+  /**
+   * Return all of the errors associated with the compilation unit.
+   * @return all of the errors associated with the compilation unit
+   */
+  List<AnalysisError> get allErrors {
+    if (_parseErrors == null) {
+      if (_resolutionErrors == null) {
+        return null;
+      }
+      return _resolutionErrors;
+    } else if (_resolutionErrors == null) {
+      return _parseErrors;
+    }
+    int parseCount = _parseErrors.length;
+    int resolutionCount = _resolutionErrors.length;
+    List<AnalysisError> errors = new List<AnalysisError>(parseCount + resolutionCount);
+    JavaSystem.arraycopy(_parseErrors, 0, errors, 0, parseCount);
+    JavaSystem.arraycopy(_resolutionErrors, 0, errors, parseCount, resolutionCount);
+    return errors;
+  }
+  SourceKind get kind => SourceKind.PART;
+  /**
+   * Return the sources for the defining compilation units for the libraries containing this source.
+   * @return the sources for the defining compilation units for the libraries containing this source
+   */
+  List<Source> get librarySources {
+    if (_librarySources == null) {
+      return Source.EMPTY_ARRAY;
+    }
+    return new List.from(_librarySources);
+  }
+  /**
+   * Return the parsed compilation unit, or {@code null} if the parsed compilation unit is not
+   * currently cached.
+   * @return the parsed compilation unit
+   */
+  CompilationUnit get parsedCompilationUnit => _parsedUnit;
+  /**
+   * Return the errors produced while scanning and parsing the compilation unit, or {@code null} if
+   * the errors are not currently cached.
+   * @return the errors produced while scanning and parsing the compilation unit
+   */
+  List<AnalysisError> get parseErrors => _parseErrors;
+  /**
+   * Return the errors produced while resolving the compilation unit, or {@code null} if the errors
+   * are not currently cached.
+   * @return the errors produced while resolving the compilation unit
+   */
+  List<AnalysisError> get resolutionErrors => _resolutionErrors;
+  /**
+   * Return the resolved compilation unit, or {@code null} if the resolved compilation unit is not
+   * currently cached.
+   * @return the resolved compilation unit
+   */
+  CompilationUnit get resolvedCompilationUnit => _resolvedUnit;
+  /**
+   * Return {@code true} if the parsed compilation unit needs to be recomputed.
+   * @return {@code true} if the parsed compilation unit needs to be recomputed
+   */
+  bool hasInvalidParsedUnit() => identical(_parsedUnitState, CacheState.INVALID);
+  /**
+   * Return {@code true} if the parse errors needs to be recomputed.
+   * @return {@code true} if the parse errors needs to be recomputed
+   */
+  bool hasInvalidParseErrors() => identical(_parseErrorsState, CacheState.INVALID);
+  /**
+   * Return {@code true} if the resolution errors needs to be recomputed.
+   * @return {@code true} if the resolution errors needs to be recomputed
+   */
+  bool hasInvalidResolutionErrors() => identical(_resolutionErrorsState, CacheState.INVALID);
+  /**
+   * Return {@code true} if the resolved compilation unit needs to be recomputed.
+   * @return {@code true} if the resolved compilation unit needs to be recomputed
+   */
+  bool hasInvalidResolvedUnit() => identical(_resolvedUnitState, CacheState.INVALID);
+  /**
+   * Mark the parsed compilation unit as needing to be recomputed.
+   */
+  void invalidateParsedUnit() {
+    _parsedUnitState = CacheState.INVALID;
+    _parsedUnit = null;
+  }
+  /**
+   * Mark the parse errors as needing to be recomputed.
+   */
+  void invalidateParseErrors() {
+    _parseErrorsState = CacheState.INVALID;
+    _parseErrors = null;
+  }
+  /**
+   * Mark the resolution errors as needing to be recomputed.
+   */
+  void invalidateResolutionErrors() {
+    _resolutionErrorsState = CacheState.INVALID;
+    _resolutionErrors = null;
+  }
+  /**
+   * Mark the resolved compilation unit as needing to be recomputed.
+   */
+  void invalidateResolvedUnit() {
+    _resolvedUnitState = CacheState.INVALID;
+    _resolvedUnit = null;
+  }
+  /**
+   * Remove the given source from the list of sources for the defining compilation units for the
+   * libraries containing this source.
+   * @param source the source to be removed to the list
+   */
+  void removeLibrarySource(Source source) {
+    if (_librarySources != null) {
+      _librarySources.remove(source);
+      if (_librarySources.isEmpty) {
+        _librarySources = null;
+      }
+    }
+  }
+  /**
+   * Set the parsed compilation unit to the given compilation unit.
+   * <p>
+   * <b>Note:</b> Do not use this method to clear or invalidate the parsed compilation unit. Use
+   * either {@link #clear} or {@link #invalidate}.
+   * @param unit the parsed compilation unit
+   */
+  void set parsedCompilationUnit(CompilationUnit unit) {
+    _parsedUnit = unit;
+    _parsedUnitState = CacheState.VALID;
+  }
+  /**
+   * Set the errors produced while scanning and parsing the compilation unit to the given errors.
+   * <p>
+   * <b>Note:</b> Do not use this method to clear or invalidate the parse errors. Use either{@link #clear} or {@link #invalidate}.
+   * @param errors the errors produced while scanning and parsing the compilation unit
+   */
+  void set parseErrors(List<AnalysisError> errors) {
+    _parseErrors = errors;
+    _parseErrorsState = CacheState.VALID;
+  }
+  /**
+   * Set the errors produced while resolving the compilation unit to the given errors.
+   * <p>
+   * <b>Note:</b> Do not use this method to clear or invalidate the resolution errors. Use either{@link #clear} or {@link #invalidate}.
+   * @param errors the errors produced while resolving the compilation unit
+   */
+  void set resolutionErrors(List<AnalysisError> errors) {
+    _resolutionErrors = errors;
+    _resolutionErrorsState = CacheState.VALID;
+  }
+  /**
+   * Set the resolved compilation unit to the given compilation unit.
+   * <p>
+   * <b>Note:</b> Do not use this method to clear or invalidate the resolved compilation unit. Use
+   * either {@link #clear} or {@link #invalidate}.
+   * @param unit the resolved compilation unit
+   */
+  void set resolvedCompilationUnit(CompilationUnit unit) {
+    _resolvedUnit = unit;
+    _resolvedUnitState = CacheState.VALID;
+  }
+  void copyFrom(SourceInfo info) {
+    super.copyFrom(info);
+  }
+}
+/**
+ * The unique instance of the class {@code DartInfo} acts as a placeholder for Dart compilation
+ * units that have not yet had their kind computed.
+ * @coverage dart.engine
+ */
+class DartInfo extends SourceInfo {
+  /**
+   * The unique instance of this class.
+   */
+  static DartInfo _UniqueInstance = new DartInfo();
+  /**
+   * Return the unique instance of this class.
+   * @return the unique instance of this class
+   */
+  static DartInfo get instance => _UniqueInstance;
+  /**
+   * Prevent the creation of instances of this class.
+   */
+  DartInfo() : super() {
+  }
+  DartInfo copy() => this;
+  SourceKind get kind => SourceKind.UNKNOWN;
+}
+/**
+ * Instances of the class {@code HtmlUnitInfo} maintain the information cached by an analysis
+ * context about an individual HTML file.
+ * @coverage dart.engine
+ */
+class HtmlUnitInfo extends SourceInfo {
+  /**
+   * The state of the cached parsed (but not resolved) HTML unit.
+   */
+  CacheState _parsedUnitState = CacheState.INVALID;
+  /**
+   * The parsed HTML unit, or {@code null} if the parsed HTML unit is not currently cached.
+   */
+  HtmlUnit _parsedUnit;
+  /**
+   * The state of the cached parsed and resolved HTML unit.
+   */
+  CacheState _resolvedUnitState = CacheState.INVALID;
+  /**
+   * The resolved HTML unit, or {@code null} if the resolved HTML unit is not currently cached.
+   */
+  HtmlUnit _resolvedUnit;
+  /**
+   * The state of the cached HTML element.
+   */
+  CacheState _elementState = CacheState.INVALID;
+  /**
+   * The element representing the HTML file, or {@code null} if the element is not currently cached.
+   */
+  HtmlElement _element;
+  /**
+   * Initialize a newly created information holder to be empty.
+   */
+  HtmlUnitInfo() : super() {
+  }
+  /**
+   * Remove the parsed HTML unit from the cache.
+   */
+  void clearParsedUnit() {
+    _parsedUnit = null;
+  }
+  /**
+   * Remove the resolved HTML unit from the cache.
+   */
+  void clearResolvedUnit() {
+    _resolvedUnit = null;
+  }
+  HtmlUnitInfo copy() {
+    HtmlUnitInfo copy = new HtmlUnitInfo();
+    copy.copyFrom(this);
+    return copy;
+  }
+  /**
+   * Return the element representing the HTML file, or {@code null} if the element is not currently
+   * cached.
+   * @return the element representing the HTML file
+   */
+  HtmlElement get element => _element;
+  SourceKind get kind => SourceKind.HTML;
+  /**
+   * Return the parsed HTML unit, or {@code null} if the parsed HTML unit is not currently cached.
+   * @return the parsed HTML unit
+   */
+  HtmlUnit get parsedUnit => _parsedUnit;
+  /**
+   * Return the resolved HTML unit, or {@code null} if the resolved HTML unit is not currently
+   * cached.
+   * @return the resolved HTML unit
+   */
+  HtmlUnit get resolvedUnit => _resolvedUnit;
+  /**
+   * Return {@code true} if the HTML element needs to be recomputed.
+   * @return {@code true} if the HTML element needs to be recomputed
+   */
+  bool hasInvalidElement() => identical(_elementState, CacheState.INVALID);
+  /**
+   * Return {@code true} if the parsed HTML unit needs to be recomputed.
+   * @return {@code true} if the parsed HTML unit needs to be recomputed
+   */
+  bool hasInvalidParsedUnit() => identical(_parsedUnitState, CacheState.INVALID);
+  /**
+   * Return {@code true} if the resolved HTML unit needs to be recomputed.
+   * @return {@code true} if the resolved HTML unit needs to be recomputed
+   */
+  bool hasInvalidResolvedUnit() => identical(_resolvedUnitState, CacheState.INVALID);
+  /**
+   * Mark the HTML element as needing to be recomputed.
+   */
+  void invalidateElement() {
+    _elementState = CacheState.INVALID;
+    _element = null;
+  }
+  /**
+   * Mark the parsed HTML unit as needing to be recomputed.
+   */
+  void invalidateParsedUnit() {
+    _parsedUnitState = CacheState.INVALID;
+    _parsedUnit = null;
+  }
+  /**
+   * Mark the resolved HTML unit as needing to be recomputed.
+   */
+  void invalidateResolvedUnit() {
+    _resolvedUnitState = CacheState.INVALID;
+    _resolvedUnit = null;
+  }
+  /**
+   * Set the element representing the HTML file to the given element.
+   * <p>
+   * <b>Note:</b> Do not use this method to clear or invalidate the element. Use either{@link #clearElement()} or {@link #invalidateElement()}.
+   * @param element the element representing the HTML file
+   */
+  void set element(HtmlElement element19) {
+    this._element = element19;
+    _elementState = CacheState.VALID;
+  }
+  /**
+   * Set the parsed HTML unit to the given HTML unit.
+   * <p>
+   * <b>Note:</b> Do not use this method to clear or invalidate the HTML unit. Use either{@link #clearParsedUnit()} or {@link #invalidateParsedUnit()}.
+   * @param unit the result of parsing the source as an HTML unit
+   */
+  void set parsedUnit(HtmlUnit unit) {
+    _parsedUnit = unit;
+    _parsedUnitState = CacheState.VALID;
+  }
+  /**
+   * Set the resolved HTML unit to the given HTML unit.
+   * <p>
+   * <b>Note:</b> Do not use this method to clear or invalidate the HTML unit. Use either{@link #clearResolvedUnit()} or {@link #invalidateResolvedUnit()}.
+   * @param unit the result of resolving the source as an HTML unit
+   */
+  void set resolvedUnit(HtmlUnit unit) {
+    _resolvedUnit = unit;
+    _resolvedUnitState = CacheState.VALID;
+  }
+  void copyFrom(SourceInfo info) {
+    super.copyFrom(info);
+  }
+}
+/**
+ * Instances of the class {@code LibraryInfo} maintain the information cached by an analysis context
+ * about an individual library.
+ * @coverage dart.engine
+ */
+class LibraryInfo extends CompilationUnitInfo {
+  /**
+   * Mask indicating that this library is launchable: that the file has a main method.
+   */
+  static int _LAUNCHABLE = 1 << 1;
+  /**
+   * Mask indicating that the library is client code: that the library depends on the html library.
+   * If the library is not "client code", then it is referenced as "server code".
+   */
+  static int _CLIENT_CODE = 1 << 2;
+  /**
+   * The state of the cached library element.
+   */
+  CacheState _elementState = CacheState.INVALID;
+  /**
+   * The element representing the library, or {@code null} if the element is not currently cached.
+   */
+  LibraryElement _element;
+  /**
+   * The state of the cached public namespace.
+   */
+  CacheState _publicNamespaceState = CacheState.INVALID;
+  /**
+   * The public namespace of the library, or {@code null} if the namespace is not currently cached.
+   */
+  Namespace _publicNamespace;
+  /**
+   * The state of the cached client/ server flag.
+   */
+  CacheState _clientServerState = CacheState.INVALID;
+  /**
+   * The state of the cached launchable flag.
+   */
+  CacheState _launchableState = CacheState.INVALID;
+  /**
+   * An integer holding bit masks such as {@link #LAUNCHABLE} and {@link #CLIENT_CODE}.
+   */
+  int _bitmask = 0;
+  /**
+   * The sources for the HTML files that reference this library (via a script tag), or {@code null}if there are no HTML files that reference the library or if the HTML files are not yet known.
+   */
+  List<Source> _htmlSources = null;
+  /**
+   * Initialize a newly created information holder to be empty.
+   */
+  LibraryInfo() : super() {
+  }
+  /**
+   * Add the given source to the list of sources for the HTML files that reference this library.
+   * @param source the source to be added to the list
+   */
+  void addHtmlSource(Source source) {
+    if (_htmlSources == null) {
+      _htmlSources = new List<Source>();
+    }
+    _htmlSources.add(source);
+  }
+  /**
+   * Remove the library element from the cache.
+   */
+  void clearElement() {
+    _element = null;
+  }
+  /**
+   * Remove the public namespace from the cache.
+   */
+  void clearPublicNamespace() {
+    _publicNamespace = null;
+  }
+  LibraryInfo copy() {
+    LibraryInfo copy = new LibraryInfo();
+    copy.copyFrom(this);
+    return copy;
+  }
+  /**
+   * Return the element representing the library, or {@code null} if the element is not currently
+   * cached.
+   * @return the element representing the library
+   */
+  LibraryElement get element => _element;
+  /**
+   * Return the sources for the HTML files that reference this library.
+   * @return the sources for the HTML files that reference this library
+   */
+  List<Source> get htmlSources {
+    if (_htmlSources == null) {
+      return Source.EMPTY_ARRAY;
+    }
+    return new List.from(_htmlSources);
+  }
+  SourceKind get kind => SourceKind.LIBRARY;
+  /**
+   * Return the public namespace of the library, or {@code null} if the namespace is not currently
+   * cached.
+   * @return the public namespace of the library
+   */
+  Namespace get publicNamespace => _publicNamespace;
+  /**
+   * Return {@code true} if the client/ server flag needs to be recomputed.
+   * @return {@code true} if the client/ server flag needs to be recomputed
+   */
+  bool hasInvalidClientServer() => identical(_clientServerState, CacheState.INVALID);
+  /**
+   * Return {@code true} if the library element needs to be recomputed.
+   * @return {@code true} if the library element needs to be recomputed
+   */
+  bool hasInvalidElement() => identical(_elementState, CacheState.INVALID);
+  /**
+   * Return {@code true} if the launchable flag needs to be recomputed.
+   * @return {@code true} if the launchable flag needs to be recomputed
+   */
+  bool hasInvalidLaunchable() => identical(_launchableState, CacheState.INVALID);
+  /**
+   * Return {@code true} if the public namespace needs to be recomputed.
+   * @return {@code true} if the public namespace needs to be recomputed
+   */
+  bool hasInvalidPublicNamespace() => identical(_publicNamespaceState, CacheState.INVALID);
+  /**
+   * Mark the client/ server flag as needing to be recomputed.
+   */
+  void invalidateClientServer() {
+    _clientServerState = CacheState.INVALID;
+    _bitmask &= ~_CLIENT_CODE;
+  }
+  /**
+   * Mark the library element as needing to be recomputed.
+   */
+  void invalidateElement() {
+    _elementState = CacheState.INVALID;
+    _element = null;
+  }
+  /**
+   * Mark the launchable flag as needing to be recomputed.
+   */
+  void invalidateLaunchable() {
+    _launchableState = CacheState.INVALID;
+    _bitmask &= ~_LAUNCHABLE;
+  }
+  /**
+   * Mark the public namespace as needing to be recomputed.
+   */
+  void invalidatePublicNamespace() {
+    _publicNamespaceState = CacheState.INVALID;
+    _publicNamespace = null;
+  }
+  /**
+   * Return <code>true</code> if this library is client based code: the library depends on the html
+   * library.
+   * @return <code>true</code> if this library is client based code: the library depends on the html
+   * library
+   */
+  bool isClient() => (_bitmask & _CLIENT_CODE) != 0;
+  /**
+   * Return <code>true</code> if this library is launchable: the file includes a main method.
+   * @return <code>true</code> if this library is launchable: the file includes a main method
+   */
+  bool isLaunchable() => (_bitmask & _LAUNCHABLE) != 0;
+  /**
+   * Return <code>true</code> if this library is server based code: the library does not depends on
+   * the html library.
+   * @return <code>true</code> if this library is server based code: the library does not depends on
+   * the html library
+   */
+  bool isServer() => (_bitmask & _CLIENT_CODE) == 0;
+  /**
+   * Remove the given source from the list of sources for the HTML files that reference this
+   * library.
+   * @param source the source to be removed to the list
+   */
+  void removeHtmlSource(Source source) {
+    if (_htmlSources != null) {
+      _htmlSources.remove(source);
+      if (_htmlSources.isEmpty) {
+        _htmlSources = null;
+      }
+    }
+  }
+  /**
+   * Sets the value of the client/ server flag.
+   * <p>
+   * <b>Note:</b> Do not use this method to invalidate the flag, use{@link #invalidateClientServer()}.
+   * @param isClient the new value of the client flag
+   */
+  void set client(bool isClient) {
+    if (isClient) {
+      _bitmask |= _CLIENT_CODE;
+    } else {
+      _bitmask &= ~_CLIENT_CODE;
+    }
+    _clientServerState = CacheState.VALID;
+  }
+  /**
+   * Set the element representing the library to the given element.
+   * <p>
+   * <b>Note:</b> Do not use this method to clear or invalidate the element. Use either{@link #clearElement()} or {@link #invalidateElement()}.
+   * @param element the element representing the library
+   */
+  void set element(LibraryElement element20) {
+    this._element = element20;
+    _elementState = CacheState.VALID;
+  }
+  /**
+   * Sets the value of the launchable flag.
+   * <p>
+   * <b>Note:</b> Do not use this method to invalidate the flag, use {@link #invalidateLaunchable()}.
+   * @param isClient the new value of the client flag
+   */
+  void set launchable(bool launchable2) {
+    if (launchable2) {
+      _bitmask |= _LAUNCHABLE;
+    } else {
+      _bitmask &= ~_LAUNCHABLE;
+    }
+    _launchableState = CacheState.VALID;
+  }
+  /**
+   * Set the public namespace of the library to the given namespace.
+   * <p>
+   * <b>Note:</b> Do not use this method to clear or invalidate the element. Use either{@link #clearPublicNamespace()} or {@link #invalidatePublicNamespace()}.
+   * @param namespace the public namespace of the library
+   */
+  void set publicNamespace(Namespace namespace) {
+    _publicNamespace = namespace;
+    _publicNamespaceState = CacheState.VALID;
+  }
+  void copyFrom(SourceInfo info) {
+    super.copyFrom(info);
+  }
+}
+/**
  * Instances of the class {@code RecordingErrorListener} implement an error listener that will
  * record the errors that are reported to it in a way that is appropriate for caching those errors
  * within an analysis context.
@@ -1009,89 +2364,86 @@
     }
   }
   void onError(AnalysisError event) {
-    Source source11 = event.source;
-    List<AnalysisError> errorsForSource = _errors[source11];
-    if (_errors[source11] == null) {
+    Source source9 = event.source;
+    List<AnalysisError> errorsForSource = _errors[source9];
+    if (_errors[source9] == null) {
       errorsForSource = new List<AnalysisError>();
-      _errors[source11] = errorsForSource;
+      _errors[source9] = errorsForSource;
     }
     errorsForSource.add(event);
   }
 }
 /**
- * Instances of the class {@code SourceInfo} maintain the information known by an analysis context
+ * Instances of the class {@code SourceInfo} maintain the information cached by an analysis context
  * about an individual source.
  * @coverage dart.engine
  */
-class SourceInfo {
+abstract class SourceInfo {
   /**
-   * The kind of the source.
+   * The state of the cached line information.
    */
-  SourceKind _kind;
+  CacheState _lineInfoState = CacheState.INVALID;
   /**
-   * The sources for the defining compilation units for the libraries containing the source, or{@code null} if the libraries containing the source are not yet known.
+   * The line information computed for the source, or {@code null} if the line information is not
+   * currently cached.
    */
-  List<Source> _librarySources = null;
-  SourceInfo.con1(Source source, SourceKind kind3) {
-    _jtd_constructor_163_impl(source, kind3);
-  }
-  _jtd_constructor_163_impl(Source source, SourceKind kind3) {
-    this._kind = kind3;
-  }
+  LineInfo _lineInfo;
   /**
-   * Initialize a newly created information holder to hold the same information as the given holder.
-   * @param info the information holder used to initialize this holder
+   * Initialize a newly created information holder to be empty.
    */
-  SourceInfo.con2(SourceInfo info) {
-    _jtd_constructor_164_impl(info);
-  }
-  _jtd_constructor_164_impl(SourceInfo info) {
-    _kind = info._kind;
-    _librarySources = new List<Source>.from(info._librarySources);
+  SourceInfo() : super() {
   }
   /**
-   * Add the given source to the list of sources for the defining compilation units for the
-   * libraries containing this source.
-   * @param source the source to be added to the list
+   * Remove the line information from the cache.
    */
-  void addLibrarySource(Source source) {
-    if (_librarySources == null) {
-      _librarySources = new List<Source>();
-    }
-    _librarySources.add(source);
+  void clearLineInfo() {
+    _lineInfo = null;
   }
   /**
-   * Return the kind of the source.
+   * Return a copy of this information holder.
+   * @return a copy of this information holder
+   */
+  SourceInfo copy();
+  /**
+   * Return the kind of the source, or {@code null} if the kind is not currently cached.
    * @return the kind of the source
    */
-  SourceKind get kind => _kind;
+  SourceKind get kind;
   /**
-   * Return the sources for the defining compilation units for the libraries containing this source.
-   * @return the sources for the defining compilation units for the libraries containing this source
+   * Return the line information computed for the source, or {@code null} if the line information is
+   * not currently cached.
+   * @return the line information computed for the source
    */
-  List<Source> get librarySources {
-    if (_librarySources == null) {
-      return Source.EMPTY_ARRAY;
-    }
-    return new List.from(_librarySources);
+  LineInfo get lineInfo => _lineInfo;
+  /**
+   * Return {@code true} if the line information needs to be recomputed.
+   * @return {@code true} if the line information needs to be recomputed
+   */
+  bool hasInvalidLineInfo() => identical(_lineInfoState, CacheState.INVALID);
+  /**
+   * Mark the line information as needing to be recomputed.
+   */
+  void invalidateLineInfo() {
+    _lineInfoState = CacheState.INVALID;
+    _lineInfo = null;
   }
   /**
-   * Remove the given source from the list of sources for the defining compilation units for the
-   * libraries containing this source.
-   * @param source the source to be removed to the list
+   * Set the line information for the source to the given line information.
+   * <p>
+   * <b>Note:</b> Do not use this method to clear or invalidate the element. Use either{@link #clearLineInfo()} or {@link #invalidateLineInfo()}.
+   * @param info the line information for the source
    */
-  void removeLibrarySource(Source source) {
-    _librarySources.remove(source);
-    if (_librarySources.isEmpty) {
-      _librarySources = null;
-    }
+  void set lineInfo(LineInfo info) {
+    _lineInfo = info;
+    _lineInfoState = CacheState.VALID;
   }
   /**
-   * Set the kind of the source to the given kind.
-   * @param kind the kind of the source
+   * Copy the information from the given information holder.
+   * @param info the information holder from which information will be copied
    */
-  void set kind(SourceKind kind4) {
-    this._kind = kind4;
+  void copyFrom(SourceInfo info) {
+    _lineInfoState = info._lineInfoState;
+    _lineInfo = info._lineInfo;
   }
 }
 /**
diff --git a/pkg/analyzer_experimental/lib/src/generated/error.dart b/pkg/analyzer_experimental/lib/src/generated/error.dart
index b8225a1..39e05e7 100644
--- a/pkg/analyzer_experimental/lib/src/generated/error.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/error.dart
@@ -122,8 +122,8 @@
    * the default source to be used.
    * @param source the source to be used when reporting errors
    */
-  void set source(Source source9) {
-    this._source = source9 == null ? _defaultSource : source9;
+  void set source(Source source7) {
+    this._source = source7 == null ? _defaultSource : source7;
   }
 }
 /**
@@ -165,11 +165,11 @@
    * @param errorCode the error code to be associated with this error
    * @param arguments the arguments used to build the error message
    */
-  AnalysisError.con1(Source source4, ErrorCode errorCode2, List<Object> arguments) {
-    _jtd_constructor_131_impl(source4, errorCode2, arguments);
+  AnalysisError.con1(Source source2, ErrorCode errorCode2, List<Object> arguments) {
+    _jtd_constructor_130_impl(source2, errorCode2, arguments);
   }
-  _jtd_constructor_131_impl(Source source4, ErrorCode errorCode2, List<Object> arguments) {
-    this._source = source4;
+  _jtd_constructor_130_impl(Source source2, ErrorCode errorCode2, List<Object> arguments) {
+    this._source = source2;
     this._errorCode = errorCode2;
     this._message = JavaString.format(errorCode2.message, arguments);
   }
@@ -181,11 +181,11 @@
    * @param errorCode the error code to be associated with this error
    * @param arguments the arguments used to build the error message
    */
-  AnalysisError.con2(Source source5, int offset2, int length11, ErrorCode errorCode3, List<Object> arguments) {
-    _jtd_constructor_132_impl(source5, offset2, length11, errorCode3, arguments);
+  AnalysisError.con2(Source source3, int offset2, int length11, ErrorCode errorCode3, List<Object> arguments) {
+    _jtd_constructor_131_impl(source3, offset2, length11, errorCode3, arguments);
   }
-  _jtd_constructor_132_impl(Source source5, int offset2, int length11, ErrorCode errorCode3, List<Object> arguments) {
-    this._source = source5;
+  _jtd_constructor_131_impl(Source source3, int offset2, int length11, ErrorCode errorCode3, List<Object> arguments) {
+    this._source = source3;
     this._offset = offset2;
     this._length = length11;
     this._errorCode = errorCode3;
@@ -228,8 +228,8 @@
    * Set the source in which the error occurred to the given source.
    * @param source the source in which the error occurred
    */
-  void set source(Source source6) {
-    this._source = source6;
+  void set source(Source source4) {
+    this._source = source4;
   }
   String toString() {
     JavaStringBuilder builder = new JavaStringBuilder();
@@ -540,18 +540,18 @@
    * error if <i>k</i>’s initializer list contains an initializer for a final variable <i>f</i>
    * whose declaration includes an initialization expression.
    */
-  static final CompileTimeErrorCode FIELD_INITIALIZED_IN_INITIALIZER_AND_DECLARATION = new CompileTimeErrorCode('FIELD_INITIALIZED_IN_INITIALIZER_AND_DECLARATION', 32, "");
+  static final CompileTimeErrorCode FIELD_INITIALIZED_IN_INITIALIZER_AND_DECLARATION = new CompileTimeErrorCode('FIELD_INITIALIZED_IN_INITIALIZER_AND_DECLARATION', 32, "Values cannot be set in the constructor if they are final, and have already been set");
   /**
    * 7.6.1 Generative Constructors: Let <i>k</i> be a generative constructor. It is a compile time
    * error if <i>k</i>’s initializer list contains an initializer for a variable that is initialized
    * by means of an initializing formal of <i>k</i>.
    */
-  static final CompileTimeErrorCode FIELD_INITIALIZED_IN_PARAMETER_AND_INITIALIZER = new CompileTimeErrorCode('FIELD_INITIALIZED_IN_PARAMETER_AND_INITIALIZER', 33, "");
+  static final CompileTimeErrorCode FIELD_INITIALIZED_IN_PARAMETER_AND_INITIALIZER = new CompileTimeErrorCode('FIELD_INITIALIZED_IN_PARAMETER_AND_INITIALIZER', 33, "Fields cannot be initialized in both the parameter list and the initializers");
   /**
    * 7.6.1 Generative Constructors: It is a compile-time error if an initializing formal is used by
    * a function other than a non-redirecting generative constructor.
    */
-  static final CompileTimeErrorCode FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR = new CompileTimeErrorCode('FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR', 34, "");
+  static final CompileTimeErrorCode FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR = new CompileTimeErrorCode('FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR', 34, "Initializing formal fields can only be used in constructors");
   /**
    * 5 Variables: It is a compile-time error if a final instance variable that has been initialized
    * at its point of declaration is also initialized in a constructor.
@@ -775,7 +775,7 @@
    * 12.7 Maps: It is a compile time error if either a key or a value of an entry in a constant map
    * literal is not a compile-time constant.
    */
-  static final CompileTimeErrorCode NON_CONSTANT_MAP_KEY = new CompileTimeErrorCode('NON_CONSTANT_MAP_KEY', 74, "The keys in a 'const' map must be constant");
+  static final CompileTimeErrorCode NON_CONSTANT_MAP_KEY = new CompileTimeErrorCode('NON_CONSTANT_MAP_KEY', 74, "The keys in a map must be constant");
   /**
    * 12.7 Maps: It is a compile time error if either a key or a value of an entry in a constant map
    * literal is not a compile-time constant.
@@ -856,20 +856,25 @@
    */
   static final CompileTimeErrorCode RESERVED_WORD_AS_IDENTIFIER = new CompileTimeErrorCode('RESERVED_WORD_AS_IDENTIFIER', 90, "");
   /**
+   * 12.8.1 Rethrow: It is a compile-time error if an expression of the form <i>rethrow;</i> is not
+   * enclosed within a on-catch clause.
+   */
+  static final CompileTimeErrorCode RETHROW_OUTSIDE_CATCH = new CompileTimeErrorCode('RETHROW_OUTSIDE_CATCH', 91, "rethrow must be inside of a catch clause");
+  /**
    * 13.11 Return: It is a compile-time error if a return statement of the form <i>return e;</i>
    * appears in a generative constructor.
    */
-  static final CompileTimeErrorCode RETURN_IN_GENERATIVE_CONSTRUCTOR = new CompileTimeErrorCode('RETURN_IN_GENERATIVE_CONSTRUCTOR', 91, "");
+  static final CompileTimeErrorCode RETURN_IN_GENERATIVE_CONSTRUCTOR = new CompileTimeErrorCode('RETURN_IN_GENERATIVE_CONSTRUCTOR', 92, "");
   /**
    * 6.1 Function Declarations: It is a compile-time error to preface a function declaration with
    * the built-in identifier static.
    */
-  static final CompileTimeErrorCode STATIC_TOP_LEVEL_FUNCTION = new CompileTimeErrorCode('STATIC_TOP_LEVEL_FUNCTION', 92, "");
+  static final CompileTimeErrorCode STATIC_TOP_LEVEL_FUNCTION = new CompileTimeErrorCode('STATIC_TOP_LEVEL_FUNCTION', 93, "");
   /**
    * 5 Variables: It is a compile-time error to preface a top level variable declaration with the
    * built-in identifier static.
    */
-  static final CompileTimeErrorCode STATIC_TOP_LEVEL_VARIABLE = new CompileTimeErrorCode('STATIC_TOP_LEVEL_VARIABLE', 93, "");
+  static final CompileTimeErrorCode STATIC_TOP_LEVEL_VARIABLE = new CompileTimeErrorCode('STATIC_TOP_LEVEL_VARIABLE', 94, "");
   /**
    * 12.15.4 Super Invocation: A super method invocation <i>i</i> has the form
    * <i>super.m(a<sub>1</sub>, &hellip;, a<sub>n</sub>, x<sub>n+1</sub>: a<sub>n+1</sub>, &hellip;
@@ -878,17 +883,12 @@
    * initializer list, in class Object, in a factory constructor, or in a static method or variable
    * initializer.
    */
-  static final CompileTimeErrorCode SUPER_IN_INVALID_CONTEXT = new CompileTimeErrorCode('SUPER_IN_INVALID_CONTEXT', 94, "");
+  static final CompileTimeErrorCode SUPER_IN_INVALID_CONTEXT = new CompileTimeErrorCode('SUPER_IN_INVALID_CONTEXT', 95, "");
   /**
    * 7.6.1 Generative Constructors: Let <i>k</i> be a generative constructor. It is a compile-time
    * error if a generative constructor of class Object includes a superinitializer.
    */
-  static final CompileTimeErrorCode SUPER_INITIALIZER_IN_OBJECT = new CompileTimeErrorCode('SUPER_INITIALIZER_IN_OBJECT', 95, "");
-  /**
-   * 12.8 Throw: It is a compile-time error if an expression of the form throw; is not enclosed
-   * within a on-catch clause.
-   */
-  static final CompileTimeErrorCode THROW_WITHOUT_VALUE_OUTSIDE_ON = new CompileTimeErrorCode('THROW_WITHOUT_VALUE_OUTSIDE_ON', 96, "");
+  static final CompileTimeErrorCode SUPER_INITIALIZER_IN_OBJECT = new CompileTimeErrorCode('SUPER_INITIALIZER_IN_OBJECT', 96, "");
   /**
    * 12.11 Instance Creation: It is a compile-time error if a constructor of a non-generic type
    * invoked by a new expression or a constant object expression is passed any type arguments.
@@ -951,7 +951,7 @@
    * <i>n</i> type parameters.
    */
   static final CompileTimeErrorCode WRONG_NUMBER_OF_TYPE_ARGUMENTS = new CompileTimeErrorCode('WRONG_NUMBER_OF_TYPE_ARGUMENTS', 103, "");
-  static final List<CompileTimeErrorCode> values = [AMBIGUOUS_EXPORT, AMBIGUOUS_IMPORT, ARGUMENT_DEFINITION_TEST_NON_PARAMETER, BUILT_IN_IDENTIFIER_AS_TYPE, BUILT_IN_IDENTIFIER_AS_TYPE_NAME, BUILT_IN_IDENTIFIER_AS_TYPEDEF_NAME, BUILT_IN_IDENTIFIER_AS_TYPE_VARIABLE_NAME, CASE_EXPRESSION_TYPE_IMPLEMENTS_EQUALS, COMPILE_TIME_CONSTANT_RAISES_EXCEPTION, COMPILE_TIME_CONSTANT_RAISES_EXCEPTION_DIVIDE_BY_ZERO, CONFLICTING_CONSTRUCTOR_NAME_AND_FIELD, CONFLICTING_CONSTRUCTOR_NAME_AND_METHOD, CONST_CONSTRUCTOR_WITH_NON_FINAL_FIELD, CONST_FORMAL_PARAMETER, CONST_INITIALIZED_WITH_NON_CONSTANT_VALUE, CONST_EVAL_THROWS_EXCEPTION, CONST_WITH_INVALID_TYPE_PARAMETERS, CONST_WITH_NON_CONST, CONST_WITH_NON_CONSTANT_ARGUMENT, CONST_WITH_NON_TYPE, CONST_WITH_TYPE_PARAMETERS, CONST_WITH_UNDEFINED_CONSTRUCTOR, DEFAULT_VALUE_IN_FUNCTION_TYPE_ALIAS, DUPLICATE_DEFINITION, DUPLICATE_MEMBER_NAME, DUPLICATE_MEMBER_NAME_INSTANCE_STATIC, DUPLICATE_NAMED_ARGUMENT, EXPORT_OF_NON_LIBRARY, EXTENDS_NON_CLASS, EXTENDS_DISALLOWED_CLASS, IMPLEMENTS_DISALLOWED_CLASS, FIELD_INITIALIZED_BY_MULTIPLE_INITIALIZERS, FIELD_INITIALIZED_IN_INITIALIZER_AND_DECLARATION, FIELD_INITIALIZED_IN_PARAMETER_AND_INITIALIZER, FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR, FINAL_INITIALIZED_IN_DECLARATION_AND_CONSTRUCTOR, FINAL_INITIALIZED_MULTIPLE_TIMES, FINAL_NOT_INITIALIZED, GETTER_AND_METHOD_WITH_SAME_NAME, IMPLEMENTS_DYNAMIC, IMPLEMENTS_NON_CLASS, IMPLEMENTS_REPEATED, IMPLEMENTS_SELF, IMPORT_DUPLICATED_LIBRARY_NAME, IMPORT_OF_NON_LIBRARY, INCONSITENT_CASE_EXPRESSION_TYPES, INITIALIZER_FOR_NON_EXISTANT_FIELD, INVALID_CONSTANT, INVALID_CONSTRUCTOR_NAME, INVALID_FACTORY_NAME_NOT_A_CLASS, INVALID_OVERRIDE_DEFAULT_VALUE, INVALID_OVERRIDE_NAMED, INVALID_OVERRIDE_POSITIONAL, INVALID_OVERRIDE_REQUIRED, INVALID_REFERENCE_TO_THIS, INVALID_TYPE_ARGUMENT_FOR_KEY, INVALID_TYPE_ARGUMENT_IN_CONST_LIST, INVALID_TYPE_ARGUMENT_IN_CONST_MAP, INVALID_VARIABLE_IN_INITIALIZER, LABEL_IN_OUTER_SCOPE, LABEL_UNDEFINED, MEMBER_WITH_CLASS_NAME, MIXIN_DECLARES_CONSTRUCTOR, MIXIN_INHERITS_FROM_NOT_OBJECT, MIXIN_OF_NON_CLASS, MIXIN_OF_NON_MIXIN, MIXIN_REFERENCES_SUPER, MIXIN_WITH_NON_CLASS_SUPERCLASS, MULTIPLE_SUPER_INITIALIZERS, NEW_WITH_INVALID_TYPE_PARAMETERS, NON_CONST_MAP_AS_EXPRESSION_STATEMENT, NON_CONSTANT_CASE_EXPRESSION, NON_CONSTANT_DEFAULT_VALUE, NON_CONSTANT_LIST_ELEMENT, NON_CONSTANT_MAP_KEY, NON_CONSTANT_MAP_VALUE, NON_CONSTANT_VALUE_IN_INITIALIZER, OBJECT_CANNOT_EXTEND_ANOTHER_CLASS, OPTIONAL_PARAMETER_IN_OPERATOR, OVERRIDE_MISSING_NAMED_PARAMETERS, OVERRIDE_MISSING_REQUIRED_PARAMETERS, PART_OF_NON_PART, PREFIX_COLLIDES_WITH_TOP_LEVEL_MEMBER, PRIVATE_OPTIONAL_PARAMETER, RECURSIVE_COMPILE_TIME_CONSTANT, RECURSIVE_FACTORY_REDIRECT, RECURSIVE_FUNCTION_TYPE_ALIAS, RECURSIVE_INTERFACE_INHERITANCE, REDIRECT_TO_NON_CONST_CONSTRUCTOR, REFERENCE_TO_DECLARED_VARIABLE_IN_INITIALIZER, RESERVED_WORD_AS_IDENTIFIER, RETURN_IN_GENERATIVE_CONSTRUCTOR, STATIC_TOP_LEVEL_FUNCTION, STATIC_TOP_LEVEL_VARIABLE, SUPER_IN_INVALID_CONTEXT, SUPER_INITIALIZER_IN_OBJECT, THROW_WITHOUT_VALUE_OUTSIDE_ON, TYPE_ARGUMENTS_FOR_NON_GENERIC_CLASS, UNDEFINED_CONSTRUCTOR_IN_INITIALIZER, UNINITIALIZED_FINAL_FIELD, URI_WITH_INTERPOLATION, WRONG_NUMBER_OF_PARAMETERS_FOR_OPERATOR, WRONG_NUMBER_OF_PARAMETERS_FOR_SETTER, WRONG_NUMBER_OF_TYPE_ARGUMENTS];
+  static final List<CompileTimeErrorCode> values = [AMBIGUOUS_EXPORT, AMBIGUOUS_IMPORT, ARGUMENT_DEFINITION_TEST_NON_PARAMETER, BUILT_IN_IDENTIFIER_AS_TYPE, BUILT_IN_IDENTIFIER_AS_TYPE_NAME, BUILT_IN_IDENTIFIER_AS_TYPEDEF_NAME, BUILT_IN_IDENTIFIER_AS_TYPE_VARIABLE_NAME, CASE_EXPRESSION_TYPE_IMPLEMENTS_EQUALS, COMPILE_TIME_CONSTANT_RAISES_EXCEPTION, COMPILE_TIME_CONSTANT_RAISES_EXCEPTION_DIVIDE_BY_ZERO, CONFLICTING_CONSTRUCTOR_NAME_AND_FIELD, CONFLICTING_CONSTRUCTOR_NAME_AND_METHOD, CONST_CONSTRUCTOR_WITH_NON_FINAL_FIELD, CONST_FORMAL_PARAMETER, CONST_INITIALIZED_WITH_NON_CONSTANT_VALUE, CONST_EVAL_THROWS_EXCEPTION, CONST_WITH_INVALID_TYPE_PARAMETERS, CONST_WITH_NON_CONST, CONST_WITH_NON_CONSTANT_ARGUMENT, CONST_WITH_NON_TYPE, CONST_WITH_TYPE_PARAMETERS, CONST_WITH_UNDEFINED_CONSTRUCTOR, DEFAULT_VALUE_IN_FUNCTION_TYPE_ALIAS, DUPLICATE_DEFINITION, DUPLICATE_MEMBER_NAME, DUPLICATE_MEMBER_NAME_INSTANCE_STATIC, DUPLICATE_NAMED_ARGUMENT, EXPORT_OF_NON_LIBRARY, EXTENDS_NON_CLASS, EXTENDS_DISALLOWED_CLASS, IMPLEMENTS_DISALLOWED_CLASS, FIELD_INITIALIZED_BY_MULTIPLE_INITIALIZERS, FIELD_INITIALIZED_IN_INITIALIZER_AND_DECLARATION, FIELD_INITIALIZED_IN_PARAMETER_AND_INITIALIZER, FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR, FINAL_INITIALIZED_IN_DECLARATION_AND_CONSTRUCTOR, FINAL_INITIALIZED_MULTIPLE_TIMES, FINAL_NOT_INITIALIZED, GETTER_AND_METHOD_WITH_SAME_NAME, IMPLEMENTS_DYNAMIC, IMPLEMENTS_NON_CLASS, IMPLEMENTS_REPEATED, IMPLEMENTS_SELF, IMPORT_DUPLICATED_LIBRARY_NAME, IMPORT_OF_NON_LIBRARY, INCONSITENT_CASE_EXPRESSION_TYPES, INITIALIZER_FOR_NON_EXISTANT_FIELD, INVALID_CONSTANT, INVALID_CONSTRUCTOR_NAME, INVALID_FACTORY_NAME_NOT_A_CLASS, INVALID_OVERRIDE_DEFAULT_VALUE, INVALID_OVERRIDE_NAMED, INVALID_OVERRIDE_POSITIONAL, INVALID_OVERRIDE_REQUIRED, INVALID_REFERENCE_TO_THIS, INVALID_TYPE_ARGUMENT_FOR_KEY, INVALID_TYPE_ARGUMENT_IN_CONST_LIST, INVALID_TYPE_ARGUMENT_IN_CONST_MAP, INVALID_VARIABLE_IN_INITIALIZER, LABEL_IN_OUTER_SCOPE, LABEL_UNDEFINED, MEMBER_WITH_CLASS_NAME, MIXIN_DECLARES_CONSTRUCTOR, MIXIN_INHERITS_FROM_NOT_OBJECT, MIXIN_OF_NON_CLASS, MIXIN_OF_NON_MIXIN, MIXIN_REFERENCES_SUPER, MIXIN_WITH_NON_CLASS_SUPERCLASS, MULTIPLE_SUPER_INITIALIZERS, NEW_WITH_INVALID_TYPE_PARAMETERS, NON_CONST_MAP_AS_EXPRESSION_STATEMENT, NON_CONSTANT_CASE_EXPRESSION, NON_CONSTANT_DEFAULT_VALUE, NON_CONSTANT_LIST_ELEMENT, NON_CONSTANT_MAP_KEY, NON_CONSTANT_MAP_VALUE, NON_CONSTANT_VALUE_IN_INITIALIZER, OBJECT_CANNOT_EXTEND_ANOTHER_CLASS, OPTIONAL_PARAMETER_IN_OPERATOR, OVERRIDE_MISSING_NAMED_PARAMETERS, OVERRIDE_MISSING_REQUIRED_PARAMETERS, PART_OF_NON_PART, PREFIX_COLLIDES_WITH_TOP_LEVEL_MEMBER, PRIVATE_OPTIONAL_PARAMETER, RECURSIVE_COMPILE_TIME_CONSTANT, RECURSIVE_FACTORY_REDIRECT, RECURSIVE_FUNCTION_TYPE_ALIAS, RECURSIVE_INTERFACE_INHERITANCE, REDIRECT_TO_NON_CONST_CONSTRUCTOR, REFERENCE_TO_DECLARED_VARIABLE_IN_INITIALIZER, RESERVED_WORD_AS_IDENTIFIER, RETHROW_OUTSIDE_CATCH, RETURN_IN_GENERATIVE_CONSTRUCTOR, STATIC_TOP_LEVEL_FUNCTION, STATIC_TOP_LEVEL_VARIABLE, SUPER_IN_INVALID_CONTEXT, SUPER_INITIALIZER_IN_OBJECT, TYPE_ARGUMENTS_FOR_NON_GENERIC_CLASS, UNDEFINED_CONSTRUCTOR_IN_INITIALIZER, UNINITIALIZED_FINAL_FIELD, URI_WITH_INTERPOLATION, WRONG_NUMBER_OF_PARAMETERS_FOR_OPERATOR, WRONG_NUMBER_OF_PARAMETERS_FOR_SETTER, WRONG_NUMBER_OF_TYPE_ARGUMENTS];
   final String __name;
   final int __ordinal;
   int get ordinal => __ordinal;
diff --git a/pkg/analyzer_experimental/lib/src/generated/html.dart b/pkg/analyzer_experimental/lib/src/generated/html.dart
index f3c33b8..3ec31be 100644
--- a/pkg/analyzer_experimental/lib/src/generated/html.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/html.dart
@@ -42,10 +42,10 @@
    * @param offset the offset from the beginning of the file to the first character in the token
    */
   Token.con1(TokenType type, int offset) {
-    _jtd_constructor_149_impl(type, offset);
+    _jtd_constructor_148_impl(type, offset);
   }
-  _jtd_constructor_149_impl(TokenType type, int offset) {
-    _jtd_constructor_150_impl(type, offset, type.lexeme);
+  _jtd_constructor_148_impl(TokenType type, int offset) {
+    _jtd_constructor_149_impl(type, offset, type.lexeme);
   }
   /**
    * Initialize a newly created token.
@@ -54,9 +54,9 @@
    * @param value the lexeme represented by this token (not {@code null})
    */
   Token.con2(TokenType type4, int offset3, String value7) {
-    _jtd_constructor_150_impl(type4, offset3, value7);
+    _jtd_constructor_149_impl(type4, offset3, value7);
   }
-  _jtd_constructor_150_impl(TokenType type4, int offset3, String value7) {
+  _jtd_constructor_149_impl(TokenType type4, int offset3, String value7) {
     this._type = type4;
     this._value = value7;
     this._offset = offset3;
@@ -626,7 +626,7 @@
   /**
    * The buffer from which characters will be read.
    */
-  CharBuffer _buffer;
+  CharSequence _buffer;
   /**
    * The number of characters in the buffer.
    */
@@ -640,7 +640,7 @@
    * @param source the source being scanned
    * @param buffer the buffer from which characters will be read
    */
-  CharBufferScanner(Source source, CharBuffer buffer) : super(source) {
+  CharBufferScanner(Source source, CharSequence buffer) : super(source) {
     this._buffer = buffer;
     this._bufferLength = buffer.length();
     this._charOffset = -1;
diff --git a/pkg/analyzer_experimental/lib/src/generated/instrumentation.dart b/pkg/analyzer_experimental/lib/src/generated/instrumentation.dart
index c01a787..1de88d7 100644
--- a/pkg/analyzer_experimental/lib/src/generated/instrumentation.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/instrumentation.dart
@@ -34,12 +34,12 @@
   /**
    * A builder that will silently ignore all data and logging requests.
    */
-  static InstrumentationBuilder _NULL_INSTRUMENTATION_BUILDER = new InstrumentationBuilder_8();
+  static InstrumentationBuilder _NULL_INSTRUMENTATION_BUILDER = new InstrumentationBuilder_9();
   /**
    * An instrumentation logger that can be used when no other instrumentation logger has been
    * configured. This logger will silently ignore all data and logging requests.
    */
-  static InstrumentationLogger _NULL_LOGGER = new InstrumentationLogger_9();
+  static InstrumentationLogger _NULL_LOGGER = new InstrumentationLogger_10();
   /**
    * The current instrumentation logger.
    */
@@ -74,7 +74,7 @@
   Instrumentation() {
   }
 }
-class InstrumentationBuilder_8 implements InstrumentationBuilder {
+class InstrumentationBuilder_9 implements InstrumentationBuilder {
   InstrumentationBuilder data(String name, bool value) => this;
   InstrumentationBuilder data2(String name, int value) => this;
   InstrumentationBuilder data3(String name, String value) => this;
@@ -87,7 +87,7 @@
   InstrumentationBuilder metric3(String name, String value) => this;
   InstrumentationBuilder metric4(String name, List<String> value) => this;
 }
-class InstrumentationLogger_9 implements InstrumentationLogger {
+class InstrumentationLogger_10 implements InstrumentationLogger {
   InstrumentationBuilder createBuilder(String name) => Instrumentation._NULL_INSTRUMENTATION_BUILDER;
 }
 /**
diff --git a/pkg/analyzer_experimental/lib/src/generated/java_core.dart b/pkg/analyzer_experimental/lib/src/generated/java_core.dart
index 877ce04..900c2ca 100644
--- a/pkg/analyzer_experimental/lib/src/generated/java_core.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/java_core.dart
@@ -108,15 +108,20 @@
   }
 }
 
-class CharBuffer {
+class CharSequence {
   final String _content;
-  CharBuffer(this._content);
-  static CharBuffer wrap(String content) => new CharBuffer(content);
+  CharSequence(this._content);
+  static CharSequence wrap(String content) => new CharBuffer(content);
   int charAt(int index) => _content.codeUnitAt(index);
   int length() => _content.length;
   String subSequence(int start, int end) => _content.substring(start, end);
 }
 
+class CharBuffer extends CharSequence {
+  CharBuffer(String content) : super(content);
+  static CharBuffer wrap(String content) => new CharBuffer(content);
+}
+
 class JavaString {
   static String format(String fmt, List args) {
     return fmt;
diff --git a/pkg/analyzer_experimental/lib/src/generated/java_io.dart b/pkg/analyzer_experimental/lib/src/generated/java_io.dart
index 53c2546..b5ac6d9 100644
--- a/pkg/analyzer_experimental/lib/src/generated/java_io.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/java_io.dart
@@ -81,6 +81,9 @@
     }
     return false;
   }
+  bool isDirectory() {
+    return _newDirectory().existsSync();
+  }
   Uri toURI() => new Uri.fromComponents(path: _path.toString());
   String readAsStringSync() => _newFile().readAsStringSync();
   int lastModified() => _newFile().lastModifiedSync().millisecondsSinceEpoch;
diff --git a/pkg/analyzer_experimental/lib/src/generated/parser.dart b/pkg/analyzer_experimental/lib/src/generated/parser.dart
index ee8a24c..7593ab6 100644
--- a/pkg/analyzer_experimental/lib/src/generated/parser.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/parser.dart
@@ -10,7 +10,7 @@
 import 'source.dart';
 import 'scanner.dart';
 import 'ast.dart';
-import 'package:analyzer_experimental/src/generated/utilities_dart.dart';
+import 'utilities_dart.dart';
 
 /**
  * Instances of the class {@code CommentAndMetadata} implement a simple data-holder for a method
@@ -554,8 +554,8 @@
       token = token.next.next;
     }
     if (identical(token.type, TokenType.KEYWORD)) {
-      Keyword keyword29 = ((token as KeywordToken)).keyword;
-      return identical(keyword29, Keyword.CASE) || identical(keyword29, Keyword.DEFAULT);
+      Keyword keyword30 = ((token as KeywordToken)).keyword;
+      return identical(keyword30, Keyword.CASE) || identical(keyword30, Keyword.DEFAULT);
     }
     return false;
   }
@@ -598,7 +598,7 @@
    * @param keyword the keyword that is being tested for
    * @return {@code true} if the given token matches the given keyword
    */
-  bool matches3(Token token, Keyword keyword37) => identical(token.type, TokenType.KEYWORD) && identical(((token as KeywordToken)).keyword, keyword37);
+  bool matches3(Token token, Keyword keyword38) => identical(token.type, TokenType.KEYWORD) && identical(((token as KeywordToken)).keyword, keyword38);
   /**
    * Return {@code true} if the given token has the given type.
    * @param token the token being tested
@@ -1351,7 +1351,7 @@
     }
     try {
       List<bool> errorFound = [false];
-      AnalysisErrorListener listener = new AnalysisErrorListener_7(errorFound);
+      AnalysisErrorListener listener = new AnalysisErrorListener_8(errorFound);
       StringScanner scanner = new StringScanner(null, referenceSource, listener);
       scanner.setSourceStart(1, 1, sourceOffset);
       Token firstToken = scanner.tokenize();
@@ -1382,7 +1382,7 @@
         } else {
         }
       }
-    } on JavaException catch (exception) {
+    } catch (exception) {
     }
     return null;
   }
@@ -1548,7 +1548,7 @@
         if (matchesIdentifier()) {
           if (matchesAny(peek(), [TokenType.EQ, TokenType.COMMA, TokenType.SEMICOLON])) {
             reportError(ParserErrorCode.VOID_VARIABLE, returnType, []);
-            return new TopLevelVariableDeclaration.full(commentAndMetadata.comment, commentAndMetadata.metadata, parseVariableDeclarationList2(validateModifiersForTopLevelVariable(modifiers), null), expect2(TokenType.SEMICOLON));
+            return new TopLevelVariableDeclaration.full(commentAndMetadata.comment, commentAndMetadata.metadata, parseVariableDeclarationList2(null, validateModifiersForTopLevelVariable(modifiers), null), expect2(TokenType.SEMICOLON));
           }
         }
         return null;
@@ -1564,7 +1564,7 @@
       validateModifiersForTopLevelFunction(modifiers);
       return parseFunctionDeclaration(commentAndMetadata, modifiers.externalKeyword, null);
     } else if (matchesAny(peek(), [TokenType.EQ, TokenType.COMMA, TokenType.SEMICOLON])) {
-      return new TopLevelVariableDeclaration.full(commentAndMetadata.comment, commentAndMetadata.metadata, parseVariableDeclarationList2(validateModifiersForTopLevelVariable(modifiers), null), expect2(TokenType.SEMICOLON));
+      return new TopLevelVariableDeclaration.full(commentAndMetadata.comment, commentAndMetadata.metadata, parseVariableDeclarationList2(null, validateModifiersForTopLevelVariable(modifiers), null), expect2(TokenType.SEMICOLON));
     }
     TypeName returnType = parseReturnType();
     if (matches(Keyword.GET) || matches(Keyword.SET)) {
@@ -1577,7 +1577,7 @@
       validateModifiersForTopLevelFunction(modifiers);
       return parseFunctionDeclaration(commentAndMetadata, modifiers.externalKeyword, returnType);
     }
-    return new TopLevelVariableDeclaration.full(commentAndMetadata.comment, commentAndMetadata.metadata, parseVariableDeclarationList2(validateModifiersForTopLevelVariable(modifiers), returnType), expect2(TokenType.SEMICOLON));
+    return new TopLevelVariableDeclaration.full(commentAndMetadata.comment, commentAndMetadata.metadata, parseVariableDeclarationList2(null, validateModifiersForTopLevelVariable(modifiers), returnType), expect2(TokenType.SEMICOLON));
   }
   /**
    * Parse a conditional expression.
@@ -1732,16 +1732,6 @@
     return new ContinueStatement.full(continueKeyword, label, semicolon);
   }
   /**
-   * Parse a declared identifier declaration.
-   * @param commentAndMetadata the metadata to be associated with the directive
-   * @return the declared identifier that was parsed
-   */
-  DeclaredIdentifier parseDeclaredIdentifier(CommentAndMetadata commentAndMetadata) {
-    FinalConstVarOrType finalConstVarOrType = parseFinalConstVarOrType(false);
-    SimpleIdentifier identifier = parseSimpleIdentifier();
-    return new DeclaredIdentifier.full(commentAndMetadata.comment, commentAndMetadata.metadata, finalConstVarOrType.keyword, finalConstVarOrType.type, identifier);
-  }
-  /**
    * Parse a directive.
    * <pre>
    * directive ::=
@@ -1885,6 +1875,8 @@
   Expression parseExpression2() {
     if (matches(Keyword.THROW)) {
       return parseThrowExpression();
+    } else if (matches(Keyword.RETHROW)) {
+      return parseRethrowExpression();
     }
     Expression expression = parseConditionalExpression();
     TokenType tokenType = _currentToken.type;
@@ -1934,6 +1926,8 @@
   Expression parseExpressionWithoutCascade() {
     if (matches(Keyword.THROW)) {
       return parseThrowExpressionWithoutCascade();
+    } else if (matches(Keyword.RETHROW)) {
+      return parseRethrowExpression();
     }
     Expression expression = parseConditionalExpression();
     if (_currentToken.type.isAssignmentOperator()) {
@@ -2180,9 +2174,9 @@
           List<VariableDeclaration> variables = new List<VariableDeclaration>();
           SimpleIdentifier variableName = parseSimpleIdentifier();
           variables.add(new VariableDeclaration.full(null, null, variableName, null, null));
-          variableList = new VariableDeclarationList.full(null, null, variables);
+          variableList = new VariableDeclarationList.full(commentAndMetadata.comment, commentAndMetadata.metadata, null, null, variables);
         } else if (isInitializedVariableDeclaration()) {
-          variableList = parseVariableDeclarationList();
+          variableList = parseVariableDeclarationList(commentAndMetadata);
         } else {
           initialization = parseExpression2();
         }
@@ -2516,7 +2510,7 @@
    * @return the getter that was parsed
    */
   FieldDeclaration parseInitializedIdentifierList(CommentAndMetadata commentAndMetadata, Token staticKeyword, Token keyword, TypeName type) {
-    VariableDeclarationList fieldList = parseVariableDeclarationList2(keyword, type);
+    VariableDeclarationList fieldList = parseVariableDeclarationList2(null, keyword, type);
     return new FieldDeclaration.full(commentAndMetadata.comment, commentAndMetadata.metadata, staticKeyword, fieldList, expect2(TokenType.SEMICOLON));
   }
   /**
@@ -2907,32 +2901,34 @@
       }
       return parseBlock();
     } else if (matches5(TokenType.KEYWORD) && !((_currentToken as KeywordToken)).keyword.isPseudoKeyword()) {
-      Keyword keyword30 = ((_currentToken as KeywordToken)).keyword;
-      if (identical(keyword30, Keyword.ASSERT)) {
+      Keyword keyword31 = ((_currentToken as KeywordToken)).keyword;
+      if (identical(keyword31, Keyword.ASSERT)) {
         return parseAssertStatement();
-      } else if (identical(keyword30, Keyword.BREAK)) {
+      } else if (identical(keyword31, Keyword.BREAK)) {
         return parseBreakStatement();
-      } else if (identical(keyword30, Keyword.CONTINUE)) {
+      } else if (identical(keyword31, Keyword.CONTINUE)) {
         return parseContinueStatement();
-      } else if (identical(keyword30, Keyword.DO)) {
+      } else if (identical(keyword31, Keyword.DO)) {
         return parseDoStatement();
-      } else if (identical(keyword30, Keyword.FOR)) {
+      } else if (identical(keyword31, Keyword.FOR)) {
         return parseForStatement();
-      } else if (identical(keyword30, Keyword.IF)) {
+      } else if (identical(keyword31, Keyword.IF)) {
         return parseIfStatement();
-      } else if (identical(keyword30, Keyword.RETURN)) {
+      } else if (identical(keyword31, Keyword.RETHROW)) {
+        return new ExpressionStatement.full(parseRethrowExpression(), expect2(TokenType.SEMICOLON));
+      } else if (identical(keyword31, Keyword.RETURN)) {
         return parseReturnStatement();
-      } else if (identical(keyword30, Keyword.SWITCH)) {
+      } else if (identical(keyword31, Keyword.SWITCH)) {
         return parseSwitchStatement();
-      } else if (identical(keyword30, Keyword.THROW)) {
+      } else if (identical(keyword31, Keyword.THROW)) {
         return new ExpressionStatement.full(parseThrowExpression(), expect2(TokenType.SEMICOLON));
-      } else if (identical(keyword30, Keyword.TRY)) {
+      } else if (identical(keyword31, Keyword.TRY)) {
         return parseTryStatement();
-      } else if (identical(keyword30, Keyword.WHILE)) {
+      } else if (identical(keyword31, Keyword.WHILE)) {
         return parseWhileStatement();
-      } else if (identical(keyword30, Keyword.VAR) || identical(keyword30, Keyword.FINAL)) {
-        return parseVariableDeclarationStatement();
-      } else if (identical(keyword30, Keyword.VOID)) {
+      } else if (identical(keyword31, Keyword.VAR) || identical(keyword31, Keyword.FINAL)) {
+        return parseVariableDeclarationStatement(commentAndMetadata);
+      } else if (identical(keyword31, Keyword.VOID)) {
         TypeName returnType = parseReturnType();
         if (matchesIdentifier() && matchesAny(peek(), [TokenType.OPEN_PAREN, TokenType.OPEN_CURLY_BRACKET, TokenType.FUNCTION])) {
           return parseFunctionDeclarationStatement2(commentAndMetadata, returnType);
@@ -2940,12 +2936,12 @@
           if (matchesIdentifier()) {
             if (matchesAny(peek(), [TokenType.EQ, TokenType.COMMA, TokenType.SEMICOLON])) {
               reportError(ParserErrorCode.VOID_VARIABLE, returnType, []);
-              return parseVariableDeclarationStatement();
+              return parseVariableDeclarationStatement(commentAndMetadata);
             }
           }
           return null;
         }
-      } else if (identical(keyword30, Keyword.CONST)) {
+      } else if (identical(keyword31, Keyword.CONST)) {
         if (matchesAny(peek(), [TokenType.LT, TokenType.OPEN_CURLY_BRACKET, TokenType.OPEN_SQUARE_BRACKET, TokenType.INDEX])) {
           return new ExpressionStatement.full(parseExpression2(), expect2(TokenType.SEMICOLON));
         } else if (matches4(peek(), TokenType.IDENTIFIER)) {
@@ -2956,8 +2952,8 @@
             }
           }
         }
-        return parseVariableDeclarationStatement();
-      } else if (identical(keyword30, Keyword.NEW) || identical(keyword30, Keyword.TRUE) || identical(keyword30, Keyword.FALSE) || identical(keyword30, Keyword.NULL) || identical(keyword30, Keyword.SUPER) || identical(keyword30, Keyword.THIS)) {
+        return parseVariableDeclarationStatement(commentAndMetadata);
+      } else if (identical(keyword31, Keyword.NEW) || identical(keyword31, Keyword.TRUE) || identical(keyword31, Keyword.FALSE) || identical(keyword31, Keyword.NULL) || identical(keyword31, Keyword.SUPER) || identical(keyword31, Keyword.THIS)) {
         return new ExpressionStatement.full(parseExpression2(), expect2(TokenType.SEMICOLON));
       } else {
         return null;
@@ -2965,7 +2961,7 @@
     } else if (matches5(TokenType.SEMICOLON)) {
       return parseEmptyStatement();
     } else if (isInitializedVariableDeclaration()) {
-      return parseVariableDeclarationStatement();
+      return parseVariableDeclarationStatement(commentAndMetadata);
     } else if (isFunctionDeclaration()) {
       return parseFunctionDeclarationStatement();
     } else if (matches5(TokenType.CLOSE_CURLY_BRACKET)) {
@@ -3282,6 +3278,15 @@
     return expression;
   }
   /**
+   * Parse a rethrow expression.
+   * <pre>
+   * rethrowExpression ::=
+   * 'rethrow'
+   * </pre>
+   * @return the rethrow expression that was parsed
+   */
+  Expression parseRethrowExpression() => new RethrowExpression.full(expect(Keyword.RETHROW));
+  /**
    * Parse a return statement.
    * <pre>
    * returnStatement ::=
@@ -3559,7 +3564,7 @@
    * Parse a throw expression.
    * <pre>
    * throwExpression ::=
-   * 'throw' expression? ';'
+   * 'throw' expression
    * </pre>
    * @return the throw expression that was parsed
    */
@@ -3575,7 +3580,7 @@
    * Parse a throw expression.
    * <pre>
    * throwExpressionWithoutCascade ::=
-   * 'throw' expressionWithoutCascade? ';'
+   * 'throw' expressionWithoutCascade
    * </pre>
    * @return the throw expression that was parsed
    */
@@ -3594,7 +3599,7 @@
    * 'try' block (onPart+ finallyPart? | finallyPart)
    * onPart ::=
    * catchPart block
-   * | 'on' qualified catchPart? block
+   * | 'on' type catchPart? block
    * catchPart ::=
    * 'catch' '(' identifier (',' identifier)? ')'
    * finallyPart ::=
@@ -3612,7 +3617,7 @@
       TypeName exceptionType = null;
       if (matches2(_ON)) {
         onKeyword = andAdvance;
-        exceptionType = new TypeName.full(parsePrefixedIdentifier(), null);
+        exceptionType = parseTypeName();
       }
       Token catchKeyword = null;
       Token leftParenthesis = null;
@@ -3776,6 +3781,9 @@
     } else if (_currentToken.type.isIncrementOperator()) {
       Token operator = andAdvance;
       if (matches(Keyword.SUPER)) {
+        if (matches4(peek(), TokenType.OPEN_SQUARE_BRACKET) || matches4(peek(), TokenType.PERIOD)) {
+          return new PrefixExpression.full(operator, parseUnaryExpression());
+        }
         if (identical(operator.type, TokenType.MINUS_MINUS)) {
           int offset9 = operator.offset;
           Token firstOperator = new Token(TokenType.MINUS, offset9);
@@ -3820,11 +3828,12 @@
    * variableDeclarationList ::=
    * finalConstVarOrType variableDeclaration (',' variableDeclaration)
    * </pre>
+   * @param commentAndMetadata the metadata to be associated with the variable declaration list
    * @return the variable declaration list that was parsed
    */
-  VariableDeclarationList parseVariableDeclarationList() {
+  VariableDeclarationList parseVariableDeclarationList(CommentAndMetadata commentAndMetadata) {
     FinalConstVarOrType holder = parseFinalConstVarOrType(false);
-    return parseVariableDeclarationList2(holder.keyword, holder.type);
+    return parseVariableDeclarationList2(commentAndMetadata, holder.keyword, holder.type);
   }
   /**
    * Parse a variable declaration list.
@@ -3832,19 +3841,21 @@
    * variableDeclarationList ::=
    * finalConstVarOrType variableDeclaration (',' variableDeclaration)
    * </pre>
+   * @param commentAndMetadata the metadata to be associated with the variable declaration list, or
+   * <code>null</code> if there is no attempt at parsing the comment and metadata
    * @param keyword the token representing the 'final', 'const' or 'var' keyword, or {@code null} if
    * there is no keyword
    * @param type the type of the variables in the list
    * @return the variable declaration list that was parsed
    */
-  VariableDeclarationList parseVariableDeclarationList2(Token keyword, TypeName type) {
+  VariableDeclarationList parseVariableDeclarationList2(CommentAndMetadata commentAndMetadata, Token keyword, TypeName type) {
     List<VariableDeclaration> variables = new List<VariableDeclaration>();
     variables.add(parseVariableDeclaration());
     while (matches5(TokenType.COMMA)) {
       advance();
       variables.add(parseVariableDeclaration());
     }
-    return new VariableDeclarationList.full(keyword, type, variables);
+    return new VariableDeclarationList.full(commentAndMetadata != null ? commentAndMetadata.comment : null, commentAndMetadata != null ? commentAndMetadata.metadata : null, keyword, type, variables);
   }
   /**
    * Parse a variable declaration statement.
@@ -3854,8 +3865,8 @@
    * </pre>
    * @return the variable declaration statement that was parsed
    */
-  VariableDeclarationStatement parseVariableDeclarationStatement() {
-    VariableDeclarationList variableList = parseVariableDeclarationList();
+  VariableDeclarationStatement parseVariableDeclarationStatement(CommentAndMetadata commentAndMetadata) {
+    VariableDeclarationList variableList = parseVariableDeclarationList(commentAndMetadata);
     Token semicolon = expect2(TokenType.SEMICOLON);
     return new VariableDeclarationStatement.full(variableList, semicolon);
   }
@@ -4644,9 +4655,9 @@
     }
   }
 }
-class AnalysisErrorListener_7 implements AnalysisErrorListener {
+class AnalysisErrorListener_8 implements AnalysisErrorListener {
   List<bool> errorFound;
-  AnalysisErrorListener_7(this.errorFound);
+  AnalysisErrorListener_8(this.errorFound);
   void onError(AnalysisError error) {
     errorFound[0] = true;
   }
@@ -4715,51 +4726,52 @@
   static final ParserErrorCode MISSING_CATCH_OR_FINALLY = new ParserErrorCode.con2('MISSING_CATCH_OR_FINALLY', 53, "A try statement must have either a catch or finally clause");
   static final ParserErrorCode MISSING_CLASS_BODY = new ParserErrorCode.con2('MISSING_CLASS_BODY', 54, "A class definition must have a body, even if it is empty");
   static final ParserErrorCode MISSING_CONST_FINAL_VAR_OR_TYPE = new ParserErrorCode.con2('MISSING_CONST_FINAL_VAR_OR_TYPE', 55, "Variables must be declared using the keywords 'const', 'final', 'var' or a type name");
-  static final ParserErrorCode MISSING_FUNCTION_BODY = new ParserErrorCode.con2('MISSING_FUNCTION_BODY', 56, "A function body must be provided");
-  static final ParserErrorCode MISSING_FUNCTION_PARAMETERS = new ParserErrorCode.con2('MISSING_FUNCTION_PARAMETERS', 57, "Functions must have an explicit list of parameters");
-  static final ParserErrorCode MISSING_IDENTIFIER = new ParserErrorCode.con2('MISSING_IDENTIFIER', 58, "Expected an identifier");
-  static final ParserErrorCode MISSING_NAME_IN_LIBRARY_DIRECTIVE = new ParserErrorCode.con2('MISSING_NAME_IN_LIBRARY_DIRECTIVE', 59, "Library directives must include a library name");
-  static final ParserErrorCode MISSING_NAME_IN_PART_OF_DIRECTIVE = new ParserErrorCode.con2('MISSING_NAME_IN_PART_OF_DIRECTIVE', 60, "Library directives must include a library name");
-  static final ParserErrorCode MISSING_STATEMENT = new ParserErrorCode.con2('MISSING_STATEMENT', 61, "Expected a statement");
-  static final ParserErrorCode MISSING_TERMINATOR_FOR_PARAMETER_GROUP = new ParserErrorCode.con2('MISSING_TERMINATOR_FOR_PARAMETER_GROUP', 62, "There is no '%s' to close the parameter group");
-  static final ParserErrorCode MISSING_TYPEDEF_PARAMETERS = new ParserErrorCode.con2('MISSING_TYPEDEF_PARAMETERS', 63, "Type aliases for functions must have an explicit list of parameters");
-  static final ParserErrorCode MISSING_VARIABLE_IN_FOR_EACH = new ParserErrorCode.con2('MISSING_VARIABLE_IN_FOR_EACH', 64, "A loop variable must be declared in a for-each loop before the 'in', but none were found");
-  static final ParserErrorCode MIXED_PARAMETER_GROUPS = new ParserErrorCode.con2('MIXED_PARAMETER_GROUPS', 65, "Cannot have both positional and named parameters in a single parameter list");
-  static final ParserErrorCode MULTIPLE_EXTENDS_CLAUSES = new ParserErrorCode.con2('MULTIPLE_EXTENDS_CLAUSES', 66, "Each class definition can have at most one extends clause");
-  static final ParserErrorCode MULTIPLE_IMPLEMENTS_CLAUSES = new ParserErrorCode.con2('MULTIPLE_IMPLEMENTS_CLAUSES', 67, "Each class definition can have at most one implements clause");
-  static final ParserErrorCode MULTIPLE_LIBRARY_DIRECTIVES = new ParserErrorCode.con2('MULTIPLE_LIBRARY_DIRECTIVES', 68, "Only one library directive may be declared in a file");
-  static final ParserErrorCode MULTIPLE_NAMED_PARAMETER_GROUPS = new ParserErrorCode.con2('MULTIPLE_NAMED_PARAMETER_GROUPS', 69, "Cannot have multiple groups of named parameters in a single parameter list");
-  static final ParserErrorCode MULTIPLE_PART_OF_DIRECTIVES = new ParserErrorCode.con2('MULTIPLE_PART_OF_DIRECTIVES', 70, "Only one part-of directive may be declared in a file");
-  static final ParserErrorCode MULTIPLE_POSITIONAL_PARAMETER_GROUPS = new ParserErrorCode.con2('MULTIPLE_POSITIONAL_PARAMETER_GROUPS', 71, "Cannot have multiple groups of positional parameters in a single parameter list");
-  static final ParserErrorCode MULTIPLE_VARIABLES_IN_FOR_EACH = new ParserErrorCode.con2('MULTIPLE_VARIABLES_IN_FOR_EACH', 72, "A single loop variable must be declared in a for-each loop before the 'in', but %s were found");
-  static final ParserErrorCode MULTIPLE_WITH_CLAUSES = new ParserErrorCode.con2('MULTIPLE_WITH_CLAUSES', 73, "Each class definition can have at most one with clause");
-  static final ParserErrorCode NAMED_PARAMETER_OUTSIDE_GROUP = new ParserErrorCode.con2('NAMED_PARAMETER_OUTSIDE_GROUP', 74, "Named parameters must be enclosed in curly braces ('{' and '}')");
-  static final ParserErrorCode NON_CONSTRUCTOR_FACTORY = new ParserErrorCode.con2('NON_CONSTRUCTOR_FACTORY', 75, "Only constructors can be declared to be a 'factory'");
-  static final ParserErrorCode NON_IDENTIFIER_LIBRARY_NAME = new ParserErrorCode.con2('NON_IDENTIFIER_LIBRARY_NAME', 76, "The name of a library must be an identifier");
-  static final ParserErrorCode NON_PART_OF_DIRECTIVE_IN_PART = new ParserErrorCode.con2('NON_PART_OF_DIRECTIVE_IN_PART', 77, "The part-of directive must be the only directive in a part");
-  static final ParserErrorCode NON_USER_DEFINABLE_OPERATOR = new ParserErrorCode.con2('NON_USER_DEFINABLE_OPERATOR', 78, "The operator '%s' is not user definable");
-  static final ParserErrorCode POSITIONAL_AFTER_NAMED_ARGUMENT = new ParserErrorCode.con2('POSITIONAL_AFTER_NAMED_ARGUMENT', 79, "Positional arguments must occur before named arguments");
-  static final ParserErrorCode POSITIONAL_PARAMETER_OUTSIDE_GROUP = new ParserErrorCode.con2('POSITIONAL_PARAMETER_OUTSIDE_GROUP', 80, "Positional parameters must be enclosed in square brackets ('[' and ']')");
-  static final ParserErrorCode STATIC_AFTER_CONST = new ParserErrorCode.con2('STATIC_AFTER_CONST', 81, "The modifier 'static' should be before the modifier 'const'");
-  static final ParserErrorCode STATIC_AFTER_FINAL = new ParserErrorCode.con2('STATIC_AFTER_FINAL', 82, "The modifier 'static' should be before the modifier 'final'");
-  static final ParserErrorCode STATIC_AFTER_VAR = new ParserErrorCode.con2('STATIC_AFTER_VAR', 83, "The modifier 'static' should be before the modifier 'var'");
-  static final ParserErrorCode STATIC_CONSTRUCTOR = new ParserErrorCode.con2('STATIC_CONSTRUCTOR', 84, "Constructors cannot be static");
-  static final ParserErrorCode STATIC_OPERATOR = new ParserErrorCode.con2('STATIC_OPERATOR', 85, "Operators cannot be static");
-  static final ParserErrorCode STATIC_TOP_LEVEL_DECLARATION = new ParserErrorCode.con2('STATIC_TOP_LEVEL_DECLARATION', 86, "Top-level declarations cannot be declared to be 'static'");
-  static final ParserErrorCode UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP = new ParserErrorCode.con2('UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP', 87, "There is no '%s' to open a parameter group");
-  static final ParserErrorCode UNEXPECTED_TOKEN = new ParserErrorCode.con2('UNEXPECTED_TOKEN', 88, "Unexpected token '%s'");
-  static final ParserErrorCode USE_OF_UNARY_PLUS_OPERATOR = new ParserErrorCode.con2('USE_OF_UNARY_PLUS_OPERATOR', 89, "There is no unary plus operator in Dart");
-  static final ParserErrorCode WITH_BEFORE_EXTENDS = new ParserErrorCode.con2('WITH_BEFORE_EXTENDS', 90, "The extends clause must be before the with clause");
-  static final ParserErrorCode WITH_WITHOUT_EXTENDS = new ParserErrorCode.con2('WITH_WITHOUT_EXTENDS', 91, "The with clause cannot be used without an extends clause");
-  static final ParserErrorCode WRONG_SEPARATOR_FOR_NAMED_PARAMETER = new ParserErrorCode.con2('WRONG_SEPARATOR_FOR_NAMED_PARAMETER', 92, "The default value of a named parameter should be preceeded by ':'");
-  static final ParserErrorCode WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER = new ParserErrorCode.con2('WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER', 93, "The default value of a positional parameter should be preceeded by '='");
-  static final ParserErrorCode WRONG_TERMINATOR_FOR_PARAMETER_GROUP = new ParserErrorCode.con2('WRONG_TERMINATOR_FOR_PARAMETER_GROUP', 94, "Expected '%s' to close parameter group");
-  static final ParserErrorCode VAR_CLASS = new ParserErrorCode.con2('VAR_CLASS', 95, "Classes cannot be declared to be 'var'");
-  static final ParserErrorCode VAR_RETURN_TYPE = new ParserErrorCode.con2('VAR_RETURN_TYPE', 96, "The return type cannot be 'var'");
-  static final ParserErrorCode VAR_TYPEDEF = new ParserErrorCode.con2('VAR_TYPEDEF', 97, "Type aliases cannot be declared to be 'var'");
-  static final ParserErrorCode VOID_PARAMETER = new ParserErrorCode.con2('VOID_PARAMETER', 98, "Parameters cannot have a type of 'void'");
-  static final ParserErrorCode VOID_VARIABLE = new ParserErrorCode.con2('VOID_VARIABLE', 99, "Variables cannot have a type of 'void'");
-  static final List<ParserErrorCode> values = [ABSTRACT_CLASS_MEMBER, ABSTRACT_STATIC_METHOD, ABSTRACT_TOP_LEVEL_FUNCTION, ABSTRACT_TOP_LEVEL_VARIABLE, ABSTRACT_TYPEDEF, BREAK_OUTSIDE_OF_LOOP, CONST_AND_FINAL, CONST_AND_VAR, CONST_CLASS, CONST_METHOD, CONST_TYPEDEF, CONSTRUCTOR_WITH_RETURN_TYPE, CONTINUE_OUTSIDE_OF_LOOP, CONTINUE_WITHOUT_LABEL_IN_CASE, DIRECTIVE_AFTER_DECLARATION, DUPLICATE_LABEL_IN_SWITCH_STATEMENT, DUPLICATED_MODIFIER, EXPECTED_CASE_OR_DEFAULT, EXPECTED_LIST_OR_MAP_LITERAL, EXPECTED_STRING_LITERAL, EXPECTED_TOKEN, EXPORT_DIRECTIVE_AFTER_PART_DIRECTIVE, EXTERNAL_AFTER_CONST, EXTERNAL_AFTER_FACTORY, EXTERNAL_AFTER_STATIC, EXTERNAL_CLASS, EXTERNAL_CONSTRUCTOR_WITH_BODY, EXTERNAL_FIELD, EXTERNAL_GETTER_WITH_BODY, EXTERNAL_METHOD_WITH_BODY, EXTERNAL_OPERATOR_WITH_BODY, EXTERNAL_SETTER_WITH_BODY, EXTERNAL_TYPEDEF, FACTORY_TOP_LEVEL_DECLARATION, FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR, FINAL_AND_VAR, FINAL_CLASS, FINAL_CONSTRUCTOR, FINAL_METHOD, FINAL_TYPEDEF, GETTER_WITH_PARAMETERS, ILLEGAL_ASSIGNMENT_TO_NON_ASSIGNABLE, IMPLEMENTS_BEFORE_EXTENDS, IMPLEMENTS_BEFORE_WITH, IMPORT_DIRECTIVE_AFTER_PART_DIRECTIVE, INITIALIZED_VARIABLE_IN_FOR_EACH, INVALID_CODE_POINT, INVALID_COMMENT_REFERENCE, INVALID_HEX_ESCAPE, INVALID_OPERATOR_FOR_SUPER, INVALID_UNICODE_ESCAPE, LIBRARY_DIRECTIVE_NOT_FIRST, MISSING_ASSIGNABLE_SELECTOR, MISSING_CATCH_OR_FINALLY, MISSING_CLASS_BODY, MISSING_CONST_FINAL_VAR_OR_TYPE, MISSING_FUNCTION_BODY, MISSING_FUNCTION_PARAMETERS, MISSING_IDENTIFIER, MISSING_NAME_IN_LIBRARY_DIRECTIVE, MISSING_NAME_IN_PART_OF_DIRECTIVE, MISSING_STATEMENT, MISSING_TERMINATOR_FOR_PARAMETER_GROUP, MISSING_TYPEDEF_PARAMETERS, MISSING_VARIABLE_IN_FOR_EACH, MIXED_PARAMETER_GROUPS, MULTIPLE_EXTENDS_CLAUSES, MULTIPLE_IMPLEMENTS_CLAUSES, MULTIPLE_LIBRARY_DIRECTIVES, MULTIPLE_NAMED_PARAMETER_GROUPS, MULTIPLE_PART_OF_DIRECTIVES, MULTIPLE_POSITIONAL_PARAMETER_GROUPS, MULTIPLE_VARIABLES_IN_FOR_EACH, MULTIPLE_WITH_CLAUSES, NAMED_PARAMETER_OUTSIDE_GROUP, NON_CONSTRUCTOR_FACTORY, NON_IDENTIFIER_LIBRARY_NAME, NON_PART_OF_DIRECTIVE_IN_PART, NON_USER_DEFINABLE_OPERATOR, POSITIONAL_AFTER_NAMED_ARGUMENT, POSITIONAL_PARAMETER_OUTSIDE_GROUP, STATIC_AFTER_CONST, STATIC_AFTER_FINAL, STATIC_AFTER_VAR, STATIC_CONSTRUCTOR, STATIC_OPERATOR, STATIC_TOP_LEVEL_DECLARATION, UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP, UNEXPECTED_TOKEN, USE_OF_UNARY_PLUS_OPERATOR, WITH_BEFORE_EXTENDS, WITH_WITHOUT_EXTENDS, WRONG_SEPARATOR_FOR_NAMED_PARAMETER, WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER, WRONG_TERMINATOR_FOR_PARAMETER_GROUP, VAR_CLASS, VAR_RETURN_TYPE, VAR_TYPEDEF, VOID_PARAMETER, VOID_VARIABLE];
+  static final ParserErrorCode MISSING_EXPRESSION_IN_THROW = new ParserErrorCode.con2('MISSING_EXPRESSION_IN_THROW', 56, "Throw expressions must compute the object to be thrown");
+  static final ParserErrorCode MISSING_FUNCTION_BODY = new ParserErrorCode.con2('MISSING_FUNCTION_BODY', 57, "A function body must be provided");
+  static final ParserErrorCode MISSING_FUNCTION_PARAMETERS = new ParserErrorCode.con2('MISSING_FUNCTION_PARAMETERS', 58, "Functions must have an explicit list of parameters");
+  static final ParserErrorCode MISSING_IDENTIFIER = new ParserErrorCode.con2('MISSING_IDENTIFIER', 59, "Expected an identifier");
+  static final ParserErrorCode MISSING_NAME_IN_LIBRARY_DIRECTIVE = new ParserErrorCode.con2('MISSING_NAME_IN_LIBRARY_DIRECTIVE', 60, "Library directives must include a library name");
+  static final ParserErrorCode MISSING_NAME_IN_PART_OF_DIRECTIVE = new ParserErrorCode.con2('MISSING_NAME_IN_PART_OF_DIRECTIVE', 61, "Library directives must include a library name");
+  static final ParserErrorCode MISSING_STATEMENT = new ParserErrorCode.con2('MISSING_STATEMENT', 62, "Expected a statement");
+  static final ParserErrorCode MISSING_TERMINATOR_FOR_PARAMETER_GROUP = new ParserErrorCode.con2('MISSING_TERMINATOR_FOR_PARAMETER_GROUP', 63, "There is no '%s' to close the parameter group");
+  static final ParserErrorCode MISSING_TYPEDEF_PARAMETERS = new ParserErrorCode.con2('MISSING_TYPEDEF_PARAMETERS', 64, "Type aliases for functions must have an explicit list of parameters");
+  static final ParserErrorCode MISSING_VARIABLE_IN_FOR_EACH = new ParserErrorCode.con2('MISSING_VARIABLE_IN_FOR_EACH', 65, "A loop variable must be declared in a for-each loop before the 'in', but none were found");
+  static final ParserErrorCode MIXED_PARAMETER_GROUPS = new ParserErrorCode.con2('MIXED_PARAMETER_GROUPS', 66, "Cannot have both positional and named parameters in a single parameter list");
+  static final ParserErrorCode MULTIPLE_EXTENDS_CLAUSES = new ParserErrorCode.con2('MULTIPLE_EXTENDS_CLAUSES', 67, "Each class definition can have at most one extends clause");
+  static final ParserErrorCode MULTIPLE_IMPLEMENTS_CLAUSES = new ParserErrorCode.con2('MULTIPLE_IMPLEMENTS_CLAUSES', 68, "Each class definition can have at most one implements clause");
+  static final ParserErrorCode MULTIPLE_LIBRARY_DIRECTIVES = new ParserErrorCode.con2('MULTIPLE_LIBRARY_DIRECTIVES', 69, "Only one library directive may be declared in a file");
+  static final ParserErrorCode MULTIPLE_NAMED_PARAMETER_GROUPS = new ParserErrorCode.con2('MULTIPLE_NAMED_PARAMETER_GROUPS', 70, "Cannot have multiple groups of named parameters in a single parameter list");
+  static final ParserErrorCode MULTIPLE_PART_OF_DIRECTIVES = new ParserErrorCode.con2('MULTIPLE_PART_OF_DIRECTIVES', 71, "Only one part-of directive may be declared in a file");
+  static final ParserErrorCode MULTIPLE_POSITIONAL_PARAMETER_GROUPS = new ParserErrorCode.con2('MULTIPLE_POSITIONAL_PARAMETER_GROUPS', 72, "Cannot have multiple groups of positional parameters in a single parameter list");
+  static final ParserErrorCode MULTIPLE_VARIABLES_IN_FOR_EACH = new ParserErrorCode.con2('MULTIPLE_VARIABLES_IN_FOR_EACH', 73, "A single loop variable must be declared in a for-each loop before the 'in', but %s were found");
+  static final ParserErrorCode MULTIPLE_WITH_CLAUSES = new ParserErrorCode.con2('MULTIPLE_WITH_CLAUSES', 74, "Each class definition can have at most one with clause");
+  static final ParserErrorCode NAMED_PARAMETER_OUTSIDE_GROUP = new ParserErrorCode.con2('NAMED_PARAMETER_OUTSIDE_GROUP', 75, "Named parameters must be enclosed in curly braces ('{' and '}')");
+  static final ParserErrorCode NON_CONSTRUCTOR_FACTORY = new ParserErrorCode.con2('NON_CONSTRUCTOR_FACTORY', 76, "Only constructors can be declared to be a 'factory'");
+  static final ParserErrorCode NON_IDENTIFIER_LIBRARY_NAME = new ParserErrorCode.con2('NON_IDENTIFIER_LIBRARY_NAME', 77, "The name of a library must be an identifier");
+  static final ParserErrorCode NON_PART_OF_DIRECTIVE_IN_PART = new ParserErrorCode.con2('NON_PART_OF_DIRECTIVE_IN_PART', 78, "The part-of directive must be the only directive in a part");
+  static final ParserErrorCode NON_USER_DEFINABLE_OPERATOR = new ParserErrorCode.con2('NON_USER_DEFINABLE_OPERATOR', 79, "The operator '%s' is not user definable");
+  static final ParserErrorCode POSITIONAL_AFTER_NAMED_ARGUMENT = new ParserErrorCode.con2('POSITIONAL_AFTER_NAMED_ARGUMENT', 80, "Positional arguments must occur before named arguments");
+  static final ParserErrorCode POSITIONAL_PARAMETER_OUTSIDE_GROUP = new ParserErrorCode.con2('POSITIONAL_PARAMETER_OUTSIDE_GROUP', 81, "Positional parameters must be enclosed in square brackets ('[' and ']')");
+  static final ParserErrorCode STATIC_AFTER_CONST = new ParserErrorCode.con2('STATIC_AFTER_CONST', 82, "The modifier 'static' should be before the modifier 'const'");
+  static final ParserErrorCode STATIC_AFTER_FINAL = new ParserErrorCode.con2('STATIC_AFTER_FINAL', 83, "The modifier 'static' should be before the modifier 'final'");
+  static final ParserErrorCode STATIC_AFTER_VAR = new ParserErrorCode.con2('STATIC_AFTER_VAR', 84, "The modifier 'static' should be before the modifier 'var'");
+  static final ParserErrorCode STATIC_CONSTRUCTOR = new ParserErrorCode.con2('STATIC_CONSTRUCTOR', 85, "Constructors cannot be static");
+  static final ParserErrorCode STATIC_OPERATOR = new ParserErrorCode.con2('STATIC_OPERATOR', 86, "Operators cannot be static");
+  static final ParserErrorCode STATIC_TOP_LEVEL_DECLARATION = new ParserErrorCode.con2('STATIC_TOP_LEVEL_DECLARATION', 87, "Top-level declarations cannot be declared to be 'static'");
+  static final ParserErrorCode UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP = new ParserErrorCode.con2('UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP', 88, "There is no '%s' to open a parameter group");
+  static final ParserErrorCode UNEXPECTED_TOKEN = new ParserErrorCode.con2('UNEXPECTED_TOKEN', 89, "Unexpected token '%s'");
+  static final ParserErrorCode USE_OF_UNARY_PLUS_OPERATOR = new ParserErrorCode.con2('USE_OF_UNARY_PLUS_OPERATOR', 90, "There is no unary plus operator in Dart");
+  static final ParserErrorCode WITH_BEFORE_EXTENDS = new ParserErrorCode.con2('WITH_BEFORE_EXTENDS', 91, "The extends clause must be before the with clause");
+  static final ParserErrorCode WITH_WITHOUT_EXTENDS = new ParserErrorCode.con2('WITH_WITHOUT_EXTENDS', 92, "The with clause cannot be used without an extends clause");
+  static final ParserErrorCode WRONG_SEPARATOR_FOR_NAMED_PARAMETER = new ParserErrorCode.con2('WRONG_SEPARATOR_FOR_NAMED_PARAMETER', 93, "The default value of a named parameter should be preceeded by ':'");
+  static final ParserErrorCode WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER = new ParserErrorCode.con2('WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER', 94, "The default value of a positional parameter should be preceeded by '='");
+  static final ParserErrorCode WRONG_TERMINATOR_FOR_PARAMETER_GROUP = new ParserErrorCode.con2('WRONG_TERMINATOR_FOR_PARAMETER_GROUP', 95, "Expected '%s' to close parameter group");
+  static final ParserErrorCode VAR_CLASS = new ParserErrorCode.con2('VAR_CLASS', 96, "Classes cannot be declared to be 'var'");
+  static final ParserErrorCode VAR_RETURN_TYPE = new ParserErrorCode.con2('VAR_RETURN_TYPE', 97, "The return type cannot be 'var'");
+  static final ParserErrorCode VAR_TYPEDEF = new ParserErrorCode.con2('VAR_TYPEDEF', 98, "Type aliases cannot be declared to be 'var'");
+  static final ParserErrorCode VOID_PARAMETER = new ParserErrorCode.con2('VOID_PARAMETER', 99, "Parameters cannot have a type of 'void'");
+  static final ParserErrorCode VOID_VARIABLE = new ParserErrorCode.con2('VOID_VARIABLE', 100, "Variables cannot have a type of 'void'");
+  static final List<ParserErrorCode> values = [ABSTRACT_CLASS_MEMBER, ABSTRACT_STATIC_METHOD, ABSTRACT_TOP_LEVEL_FUNCTION, ABSTRACT_TOP_LEVEL_VARIABLE, ABSTRACT_TYPEDEF, BREAK_OUTSIDE_OF_LOOP, CONST_AND_FINAL, CONST_AND_VAR, CONST_CLASS, CONST_METHOD, CONST_TYPEDEF, CONSTRUCTOR_WITH_RETURN_TYPE, CONTINUE_OUTSIDE_OF_LOOP, CONTINUE_WITHOUT_LABEL_IN_CASE, DIRECTIVE_AFTER_DECLARATION, DUPLICATE_LABEL_IN_SWITCH_STATEMENT, DUPLICATED_MODIFIER, EXPECTED_CASE_OR_DEFAULT, EXPECTED_LIST_OR_MAP_LITERAL, EXPECTED_STRING_LITERAL, EXPECTED_TOKEN, EXPORT_DIRECTIVE_AFTER_PART_DIRECTIVE, EXTERNAL_AFTER_CONST, EXTERNAL_AFTER_FACTORY, EXTERNAL_AFTER_STATIC, EXTERNAL_CLASS, EXTERNAL_CONSTRUCTOR_WITH_BODY, EXTERNAL_FIELD, EXTERNAL_GETTER_WITH_BODY, EXTERNAL_METHOD_WITH_BODY, EXTERNAL_OPERATOR_WITH_BODY, EXTERNAL_SETTER_WITH_BODY, EXTERNAL_TYPEDEF, FACTORY_TOP_LEVEL_DECLARATION, FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR, FINAL_AND_VAR, FINAL_CLASS, FINAL_CONSTRUCTOR, FINAL_METHOD, FINAL_TYPEDEF, GETTER_WITH_PARAMETERS, ILLEGAL_ASSIGNMENT_TO_NON_ASSIGNABLE, IMPLEMENTS_BEFORE_EXTENDS, IMPLEMENTS_BEFORE_WITH, IMPORT_DIRECTIVE_AFTER_PART_DIRECTIVE, INITIALIZED_VARIABLE_IN_FOR_EACH, INVALID_CODE_POINT, INVALID_COMMENT_REFERENCE, INVALID_HEX_ESCAPE, INVALID_OPERATOR_FOR_SUPER, INVALID_UNICODE_ESCAPE, LIBRARY_DIRECTIVE_NOT_FIRST, MISSING_ASSIGNABLE_SELECTOR, MISSING_CATCH_OR_FINALLY, MISSING_CLASS_BODY, MISSING_CONST_FINAL_VAR_OR_TYPE, MISSING_EXPRESSION_IN_THROW, MISSING_FUNCTION_BODY, MISSING_FUNCTION_PARAMETERS, MISSING_IDENTIFIER, MISSING_NAME_IN_LIBRARY_DIRECTIVE, MISSING_NAME_IN_PART_OF_DIRECTIVE, MISSING_STATEMENT, MISSING_TERMINATOR_FOR_PARAMETER_GROUP, MISSING_TYPEDEF_PARAMETERS, MISSING_VARIABLE_IN_FOR_EACH, MIXED_PARAMETER_GROUPS, MULTIPLE_EXTENDS_CLAUSES, MULTIPLE_IMPLEMENTS_CLAUSES, MULTIPLE_LIBRARY_DIRECTIVES, MULTIPLE_NAMED_PARAMETER_GROUPS, MULTIPLE_PART_OF_DIRECTIVES, MULTIPLE_POSITIONAL_PARAMETER_GROUPS, MULTIPLE_VARIABLES_IN_FOR_EACH, MULTIPLE_WITH_CLAUSES, NAMED_PARAMETER_OUTSIDE_GROUP, NON_CONSTRUCTOR_FACTORY, NON_IDENTIFIER_LIBRARY_NAME, NON_PART_OF_DIRECTIVE_IN_PART, NON_USER_DEFINABLE_OPERATOR, POSITIONAL_AFTER_NAMED_ARGUMENT, POSITIONAL_PARAMETER_OUTSIDE_GROUP, STATIC_AFTER_CONST, STATIC_AFTER_FINAL, STATIC_AFTER_VAR, STATIC_CONSTRUCTOR, STATIC_OPERATOR, STATIC_TOP_LEVEL_DECLARATION, UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP, UNEXPECTED_TOKEN, USE_OF_UNARY_PLUS_OPERATOR, WITH_BEFORE_EXTENDS, WITH_WITHOUT_EXTENDS, WRONG_SEPARATOR_FOR_NAMED_PARAMETER, WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER, WRONG_TERMINATOR_FOR_PARAMETER_GROUP, VAR_CLASS, VAR_RETURN_TYPE, VAR_TYPEDEF, VOID_PARAMETER, VOID_VARIABLE];
   String __name;
   int __ordinal = 0;
   int get ordinal => __ordinal;
@@ -4777,9 +4789,9 @@
    * @param message the message template used to create the message to be displayed for the error
    */
   ParserErrorCode.con1(String ___name, int ___ordinal, ErrorSeverity severity2, String message2) {
-    _jtd_constructor_271_impl(___name, ___ordinal, severity2, message2);
+    _jtd_constructor_275_impl(___name, ___ordinal, severity2, message2);
   }
-  _jtd_constructor_271_impl(String ___name, int ___ordinal, ErrorSeverity severity2, String message2) {
+  _jtd_constructor_275_impl(String ___name, int ___ordinal, ErrorSeverity severity2, String message2) {
     __name = ___name;
     __ordinal = ___ordinal;
     this._severity = severity2;
@@ -4790,10 +4802,10 @@
    * @param message the message template used to create the message to be displayed for the error
    */
   ParserErrorCode.con2(String ___name, int ___ordinal, String message) {
-    _jtd_constructor_272_impl(___name, ___ordinal, message);
+    _jtd_constructor_276_impl(___name, ___ordinal, message);
   }
-  _jtd_constructor_272_impl(String ___name, int ___ordinal, String message) {
-    _jtd_constructor_271_impl(___name, ___ordinal, ErrorSeverity.ERROR, message);
+  _jtd_constructor_276_impl(String ___name, int ___ordinal, String message) {
+    _jtd_constructor_275_impl(___name, ___ordinal, ErrorSeverity.ERROR, message);
   }
   ErrorSeverity get errorSeverity => _severity;
   String get message => _message;
@@ -5392,6 +5404,10 @@
     visit(node.argumentList);
     return null;
   }
+  Object visitRethrowExpression(RethrowExpression node) {
+    _writer.print("rethrow");
+    return null;
+  }
   Object visitReturnStatement(ReturnStatement node) {
     Expression expression17 = node.expression;
     if (expression17 == null) {
diff --git a/pkg/analyzer_experimental/lib/src/generated/resolver.dart b/pkg/analyzer_experimental/lib/src/generated/resolver.dart
index 002d360..4305b1a 100644
--- a/pkg/analyzer_experimental/lib/src/generated/resolver.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/resolver.dart
@@ -29,17 +29,11 @@
    */
   AnalysisContextImpl _analysisContext;
   /**
-   * The listener to which errors will be reported.
-   */
-  AnalysisErrorListener _errorListener;
-  /**
    * Initialize a newly created compilation unit element builder.
    * @param analysisContext the analysis context in which the element model will be built
-   * @param errorListener the listener to which errors will be reported
    */
-  CompilationUnitBuilder(AnalysisContextImpl analysisContext, AnalysisErrorListener errorListener) {
+  CompilationUnitBuilder(AnalysisContextImpl analysisContext) {
     this._analysisContext = analysisContext;
-    this._errorListener = errorListener;
   }
   /**
    * Build the compilation unit element for the given source.
@@ -47,7 +41,7 @@
    * @return the compilation unit element that was built
    * @throws AnalysisException if the analysis could not be performed
    */
-  CompilationUnitElementImpl buildCompilationUnit(Source source) => buildCompilationUnit2(source, _analysisContext.parse3(source, _errorListener));
+  CompilationUnitElementImpl buildCompilationUnit(Source source) => buildCompilationUnit2(source, _analysisContext.parseCompilationUnit(source));
   /**
    * Build the compilation unit element for the given source.
    * @param source the source describing the compilation unit
@@ -55,14 +49,17 @@
    * @return the compilation unit element that was built
    * @throws AnalysisException if the analysis could not be performed
    */
-  CompilationUnitElementImpl buildCompilationUnit2(Source source15, CompilationUnit unit) {
+  CompilationUnitElementImpl buildCompilationUnit2(Source source13, CompilationUnit unit) {
+    if (unit == null) {
+      return null;
+    }
     ElementHolder holder = new ElementHolder();
     ElementBuilder builder = new ElementBuilder(holder);
     unit.accept(builder);
-    CompilationUnitElementImpl element = new CompilationUnitElementImpl(source15.shortName);
+    CompilationUnitElementImpl element = new CompilationUnitElementImpl(source13.shortName);
     element.accessors = holder.accessors;
     element.functions = holder.functions;
-    element.source = source15;
+    element.source = source13;
     element.typeAliases = holder.typeAliases;
     element.types = holder.types;
     element.topLevelVariables = holder.topLevelVariables;
@@ -188,14 +185,14 @@
   }
   Object visitDeclaredIdentifier(DeclaredIdentifier node) {
     SimpleIdentifier variableName = node.identifier;
-    sc.Token keyword27 = node.keyword;
+    sc.Token keyword28 = node.keyword;
     LocalVariableElementImpl element = new LocalVariableElementImpl(variableName);
     ForEachStatement statement = node.parent as ForEachStatement;
     int declarationEnd = node.offset + node.length;
     int statementEnd = statement.offset + statement.length;
     element.setVisibleRange(declarationEnd, statementEnd - declarationEnd - 1);
-    element.const3 = matches(keyword27, sc.Keyword.CONST);
-    element.final2 = matches(keyword27, sc.Keyword.FINAL);
+    element.const3 = matches(keyword28, sc.Keyword.CONST);
+    element.final2 = matches(keyword28, sc.Keyword.FINAL);
     _currentHolder.addLocalVariable(element);
     variableName.element = element;
     return super.visitDeclaredIdentifier(node);
@@ -485,9 +482,9 @@
     return super.visitTypeParameter(node);
   }
   Object visitVariableDeclaration(VariableDeclaration node) {
-    sc.Token keyword28 = ((node.parent as VariableDeclarationList)).keyword;
-    bool isConst = matches(keyword28, sc.Keyword.CONST);
-    bool isFinal = matches(keyword28, sc.Keyword.FINAL);
+    sc.Token keyword29 = ((node.parent as VariableDeclarationList)).keyword;
+    bool isConst = matches(keyword29, sc.Keyword.CONST);
+    bool isFinal = matches(keyword29, sc.Keyword.FINAL);
     bool hasInitializer = node.initializer != null;
     VariableElementImpl element;
     if (_inFieldContext) {
@@ -599,7 +596,7 @@
    * @param keyword the keyword being tested for
    * @return {@code true} if the given token is a token for the given keyword
    */
-  bool matches(sc.Token token, sc.Keyword keyword36) => token != null && identical(token.type, sc.TokenType.KEYWORD) && identical(((token as sc.KeywordToken)).keyword, keyword36);
+  bool matches(sc.Token token, sc.Keyword keyword37) => token != null && identical(token.type, sc.TokenType.KEYWORD) && identical(((token as sc.KeywordToken)).keyword, keyword37);
   /**
    * Make the given holder be the current holder while visiting the given node.
    * @param holder the holder that will gather elements that are built while visiting the children
@@ -747,16 +744,16 @@
    * @return the HTML element that was built
    * @throws AnalysisException if the analysis could not be performed
    */
-  HtmlElementImpl buildHtmlElement(Source source) => buildHtmlElement2(source, _context.parseHtml(source).htmlUnit);
+  HtmlElementImpl buildHtmlElement(Source source) => buildHtmlElement2(source, _context.parseHtmlUnit(source));
   /**
    * Build the HTML element for the given source.
    * @param source the source describing the compilation unit
    * @param unit the AST structure representing the HTML
    * @throws AnalysisException if the analysis could not be performed
    */
-  HtmlElementImpl buildHtmlElement2(Source source16, ht.HtmlUnit unit) {
-    HtmlElementImpl result = new HtmlElementImpl(_context, source16.shortName);
-    result.source = source16;
+  HtmlElementImpl buildHtmlElement2(Source source14, ht.HtmlUnit unit) {
+    HtmlElementImpl result = new HtmlElementImpl(_context, source14.shortName);
+    result.source = source14;
     _htmlElement = result;
     unit.accept(this);
     _htmlElement = null;
@@ -785,7 +782,7 @@
         Parser parser = new Parser(null, errorListener);
         CompilationUnit unit = parser.parseCompilationUnit(firstToken);
         try {
-          CompilationUnitBuilder builder = new CompilationUnitBuilder(_context, errorListener);
+          CompilationUnitBuilder builder = new CompilationUnitBuilder(_context);
           CompilationUnitElementImpl elem = builder.buildCompilationUnit2(htmlSource, unit);
           LibraryElementImpl library = new LibraryElementImpl(_context, null);
           library.definingCompilationUnit = elem;
@@ -992,9 +989,9 @@
     return null;
   }
   Object visitExportDirective(ExportDirective node) {
-    Element element22 = node.element;
-    if (element22 is ExportElement) {
-      resolveCombinators(((element22 as ExportElement)).exportedLibrary, node.combinators);
+    Element element26 = node.element;
+    if (element26 is ExportElement) {
+      resolveCombinators(((element26 as ExportElement)).exportedLibrary, node.combinators);
     }
     return null;
   }
@@ -1010,9 +1007,9 @@
         }
       }
     }
-    Element element23 = node.element;
-    if (element23 is ImportElement) {
-      resolveCombinators(((element23 as ImportElement)).importedLibrary, node.combinators);
+    Element element27 = node.element;
+    if (element27 is ImportElement) {
+      resolveCombinators(((element27 as ImportElement)).importedLibrary, node.combinators);
     }
     return null;
   }
@@ -1089,7 +1086,7 @@
         Element targetElement = ((target as SimpleIdentifier)).element;
         if (targetElement is PrefixElement) {
           String name9 = "${((target as SimpleIdentifier)).name}.${methodName2}";
-          Identifier functionName = new Identifier_4(name9);
+          Identifier functionName = new Identifier_5(name9);
           element = _resolver.nameScope.lookup(functionName, _resolver.definingLibrary);
         } else {
           return null;
@@ -1702,9 +1699,9 @@
    * @param node the AST node that was resolved
    * @param element the element to which the AST node was resolved
    */
-  void recordResolution(SimpleIdentifier node, Element element52) {
-    if (element52 != null) {
-      node.element = element52;
+  void recordResolution(SimpleIdentifier node, Element element58) {
+    if (element58 != null) {
+      node.element = element58;
     }
   }
   /**
@@ -1774,20 +1771,20 @@
    * @return the class that should be used in place of the argument if it is a type variable, or the
    * original argument if it isn't a type variable
    */
-  Element resolveTypeVariable(Element element53) {
-    if (element53 is TypeVariableElement) {
-      Type2 bound4 = ((element53 as TypeVariableElement)).bound;
+  Element resolveTypeVariable(Element element59) {
+    if (element59 is TypeVariableElement) {
+      Type2 bound4 = ((element59 as TypeVariableElement)).bound;
       if (bound4 == null) {
         return _resolver.typeProvider.objectType.element;
       }
       return bound4.element;
     }
-    return element53;
+    return element59;
   }
 }
-class Identifier_4 extends Identifier {
+class Identifier_5 extends Identifier {
   String name9;
-  Identifier_4(this.name9) : super();
+  Identifier_5(this.name9) : super();
   accept(ASTVisitor visitor) => null;
   sc.Token get beginToken => null;
   Element get element => null;
@@ -1850,7 +1847,7 @@
     this._analysisContext = analysisContext;
     this._errorListener = errorListener;
     this._librarySource = librarySource;
-    this._libraryElement = analysisContext.getLibraryElementOrNull(librarySource) as LibraryElementImpl;
+    this._libraryElement = analysisContext.getLibraryElement(librarySource) as LibraryElementImpl;
   }
   /**
    * Record that the given library is exported from this library.
@@ -1875,7 +1872,7 @@
   CompilationUnit getAST(Source source) {
     CompilationUnit unit = _astMap[source];
     if (unit == null) {
-      unit = _analysisContext.parse3(source, _errorListener);
+      unit = _analysisContext.parseCompilationUnit(source);
       _astMap[source] = unit;
     }
     return unit;
@@ -1944,7 +1941,11 @@
    */
   LibraryElementImpl get libraryElement {
     if (_libraryElement == null) {
-      _libraryElement = _analysisContext.getLibraryElement(_librarySource) as LibraryElementImpl;
+      try {
+        _libraryElement = _analysisContext.computeLibraryElement(_librarySource) as LibraryElementImpl;
+      } on AnalysisException catch (exception) {
+        AnalysisEngine.instance.logger.logError2("Could not compute ilbrary element for ${_librarySource.fullName}", exception);
+      }
     }
     return _libraryElement;
   }
@@ -2073,7 +2074,7 @@
    * @throws AnalysisException if the analysis could not be performed
    */
   LibraryElementImpl buildLibrary(Library library) {
-    CompilationUnitBuilder builder = new CompilationUnitBuilder(_analysisContext, _errorListener);
+    CompilationUnitBuilder builder = new CompilationUnitBuilder(_analysisContext);
     Source librarySource2 = library.librarySource;
     CompilationUnit definingCompilationUnit3 = library.definingCompilationUnit;
     CompilationUnitElementImpl definingCompilationUnitElement = builder.buildCompilationUnit2(librarySource2, definingCompilationUnit3);
@@ -2093,7 +2094,7 @@
         hasPartDirective = true;
         StringLiteral partUri = ((directive as PartDirective)).uri;
         Source partSource = library.getSource(partUri);
-        if (partSource != null) {
+        if (partSource != null && partSource.exists()) {
           CompilationUnitElementImpl part = builder.buildCompilationUnit(partSource);
           String partLibraryName = getPartLibraryName(library, partSource, directivesToResolve);
           if (partLibraryName == null) {
@@ -2182,7 +2183,7 @@
   /**
    * This error listener is used by the resolver to be able to call the listener and get back the
    * set of errors for each {@link Source}.
-   * @see #recordErrors()
+   * @see #recordResults()
    */
   RecordingErrorListener _recordingErrorListener;
   /**
@@ -2210,10 +2211,10 @@
    * @param analysisContext the analysis context in which the library is being analyzed
    */
   LibraryResolver.con1(AnalysisContextImpl analysisContext) {
-    _jtd_constructor_239_impl(analysisContext);
+    _jtd_constructor_243_impl(analysisContext);
   }
-  _jtd_constructor_239_impl(AnalysisContextImpl analysisContext) {
-    _jtd_constructor_240_impl(analysisContext, null);
+  _jtd_constructor_243_impl(AnalysisContextImpl analysisContext) {
+    _jtd_constructor_244_impl(analysisContext, null);
   }
   /**
    * Initialize a newly created library resolver to resolve libraries within the given context.
@@ -2221,15 +2222,15 @@
    * @param errorListener the listener to which analysis errors will be reported
    */
   LibraryResolver.con2(AnalysisContextImpl analysisContext2, AnalysisErrorListener additionalAnalysisErrorListener) {
-    _jtd_constructor_240_impl(analysisContext2, additionalAnalysisErrorListener);
+    _jtd_constructor_244_impl(analysisContext2, additionalAnalysisErrorListener);
   }
-  _jtd_constructor_240_impl(AnalysisContextImpl analysisContext2, AnalysisErrorListener additionalAnalysisErrorListener) {
+  _jtd_constructor_244_impl(AnalysisContextImpl analysisContext2, AnalysisErrorListener additionalAnalysisErrorListener) {
     this._analysisContext = analysisContext2;
     this._recordingErrorListener = new RecordingErrorListener();
     if (additionalAnalysisErrorListener == null) {
       this._errorListener = _recordingErrorListener;
     } else {
-      this._errorListener = new AnalysisErrorListener_5(this, additionalAnalysisErrorListener);
+      this._errorListener = new AnalysisErrorListener_6(this, additionalAnalysisErrorListener);
     }
     _coreLibrarySource = analysisContext2.sourceFactory.forUri(LibraryElementBuilder.CORE_LIBRARY_URI);
   }
@@ -2271,8 +2272,7 @@
     if (fullAnalysis) {
       runAdditionalAnalyses();
     }
-    recordLibraryElements();
-    recordErrors();
+    recordResults();
     return targetLibrary.libraryElement;
   }
   /**
@@ -2538,6 +2538,9 @@
    * @return the library object that was created
    */
   Library createLibraryOrNull(Source librarySource) {
+    if (!librarySource.exists()) {
+      return null;
+    }
     Library library = new Library(_analysisContext, _errorListener, librarySource);
     try {
       library.definingCompilationUnit;
@@ -2561,38 +2564,30 @@
     return identifiers;
   }
   /**
-   * For each library, loop through the set of all {@link CompilationUnit}s recording the set of
-   * resolution errors on each unit.
+   * Record the results of resolution with the analysis context. This includes recording
+   * <ul>
+   * <li>the resolved AST associated with each compilation unit,</li>
+   * <li>the set of resolution errors produced for each compilation unit, and</li>
+   * <li>the element models produced for each library.</li>
+   * </ul>
    */
-  void recordErrors() {
-    for (Library library in _librariesInCycles) {
-      try {
-        CompilationUnit definingUnit = library.definingCompilationUnit;
-        definingUnit.resolutionErrors = _recordingErrorListener.getErrors2(library.librarySource);
-      } on AnalysisException catch (e) {
-        throw new AnalysisException();
-      }
-      Set<Source> sources = library.compilationUnitSources;
-      for (Source source in sources) {
-        try {
-          CompilationUnit unit = library.getAST(source);
-          unit.resolutionErrors = _recordingErrorListener.getErrors2(source);
-        } on JavaException catch (e) {
-          throw new AnalysisException();
-        }
-      }
-    }
-  }
-  /**
-   * As the final step in the process, record the resolved element models with the analysis context.
-   */
-  void recordLibraryElements() {
+  void recordResults() {
     Map<Source, LibraryElement> elementMap = new Map<Source, LibraryElement>();
     for (Library library in _librariesInCycles) {
+      recordResults2(library.librarySource, library.definingCompilationUnit);
+      for (Source source in library.compilationUnitSources) {
+        recordResults2(source, library.getAST(source));
+      }
       elementMap[library.librarySource] = library.libraryElement;
     }
     _analysisContext.recordLibraryElements(elementMap);
   }
+  void recordResults2(Source source, CompilationUnit unit) {
+    List<AnalysisError> errors = _recordingErrorListener.getErrors2(source);
+    unit.resolutionErrors = errors;
+    _analysisContext.recordResolvedCompilationUnit(source, unit);
+    _analysisContext.recordResolutionErrors(source, errors, unit.lineInfo);
+  }
   /**
    * Resolve the identifiers and perform type analysis in the libraries in the current cycle.
    * @throws AnalysisException if any of the identifiers could not be resolved or if any of the
@@ -2642,10 +2637,10 @@
     }
   }
 }
-class AnalysisErrorListener_5 implements AnalysisErrorListener {
+class AnalysisErrorListener_6 implements AnalysisErrorListener {
   final LibraryResolver LibraryResolver_this;
   AnalysisErrorListener additionalAnalysisErrorListener;
-  AnalysisErrorListener_5(this.LibraryResolver_this, this.additionalAnalysisErrorListener);
+  AnalysisErrorListener_6(this.LibraryResolver_this, this.additionalAnalysisErrorListener);
   void onError(AnalysisError error) {
     additionalAnalysisErrorListener.onError(error);
     LibraryResolver_this._recordingErrorListener.onError(error);
@@ -3027,9 +3022,9 @@
   }
   Object visitVariableDeclaration(VariableDeclaration node) {
     if (node.parent.parent is! TopLevelVariableDeclaration && node.parent.parent is! FieldDeclaration) {
-      VariableElement element24 = node.element;
-      if (element24 != null) {
-        _nameScope.define(element24);
+      VariableElement element28 = node.element;
+      if (element28 != null) {
+        _nameScope.define(element28);
       }
     }
     super.visitVariableDeclaration(node);
@@ -3485,17 +3480,17 @@
    */
   Object visitPrefixedIdentifier(PrefixedIdentifier node) {
     SimpleIdentifier prefixedIdentifier = node.identifier;
-    Element element25 = prefixedIdentifier.element;
-    if (element25 is VariableElement) {
-      Type2 variableType = ((element25 as VariableElement)).type;
+    Element element29 = prefixedIdentifier.element;
+    if (element29 is VariableElement) {
+      Type2 variableType = ((element29 as VariableElement)).type;
       recordType(prefixedIdentifier, variableType);
       return recordType(node, variableType);
-    } else if (element25 is PropertyAccessorElement) {
-      Type2 propertyType = getType2((element25 as PropertyAccessorElement));
+    } else if (element29 is PropertyAccessorElement) {
+      Type2 propertyType = getType2((element29 as PropertyAccessorElement));
       recordType(prefixedIdentifier, propertyType);
       return recordType(node, propertyType);
-    } else if (element25 is MethodElement) {
-      Type2 returnType = ((element25 as MethodElement)).type;
+    } else if (element29 is MethodElement) {
+      Type2 returnType = ((element29 as MethodElement)).type;
       recordType(prefixedIdentifier, returnType);
       return recordType(node, returnType);
     } else {
@@ -3560,13 +3555,13 @@
    */
   Object visitPropertyAccess(PropertyAccess node) {
     SimpleIdentifier propertyName2 = node.propertyName;
-    Element element26 = propertyName2.element;
-    if (element26 is MethodElement) {
-      FunctionType type15 = ((element26 as MethodElement)).type;
+    Element element30 = propertyName2.element;
+    if (element30 is MethodElement) {
+      FunctionType type15 = ((element30 as MethodElement)).type;
       recordType(propertyName2, type15);
       return recordType(node, type15);
-    } else if (element26 is PropertyAccessorElement) {
-      Type2 propertyType = getType2((element26 as PropertyAccessorElement));
+    } else if (element30 is PropertyAccessorElement) {
+      Type2 propertyType = getType2((element30 as PropertyAccessorElement));
       recordType(propertyName2, propertyType);
       return recordType(node, propertyType);
     } else {
@@ -3575,6 +3570,11 @@
     return recordType(node, _dynamicType);
   }
   /**
+   * The Dart Language Specification, 12.9: <blockquote>The static type of a rethrow expression is
+   * bottom.</blockquote>
+   */
+  Object visitRethrowExpression(RethrowExpression node) => recordType(node, _typeProvider.bottomType);
+  /**
    * The Dart Language Specification, 12.30: <blockquote>Evaluation of an identifier expression
    * <i>e</i> of the form <i>id</i> proceeds as follows:
    * <p>
@@ -3617,27 +3617,27 @@
    * </blockquote>
    */
   Object visitSimpleIdentifier(SimpleIdentifier node) {
-    Element element27 = node.element;
-    if (element27 == null) {
+    Element element31 = node.element;
+    if (element31 == null) {
       return recordType(node, _dynamicType);
-    } else if (element27 is ClassElement) {
+    } else if (element31 is ClassElement) {
       if (isNotTypeLiteral(node)) {
-        return recordType(node, ((element27 as ClassElement)).type);
+        return recordType(node, ((element31 as ClassElement)).type);
       }
       return recordType(node, _typeProvider.typeType);
-    } else if (element27 is TypeVariableElement) {
-      return recordType(node, ((element27 as TypeVariableElement)).type);
-    } else if (element27 is FunctionTypeAliasElement) {
-      return recordType(node, ((element27 as FunctionTypeAliasElement)).type);
-    } else if (element27 is VariableElement) {
-      return recordType(node, ((element27 as VariableElement)).type);
-    } else if (element27 is MethodElement) {
-      return recordType(node, ((element27 as MethodElement)).type);
-    } else if (element27 is PropertyAccessorElement) {
-      return recordType(node, getType2((element27 as PropertyAccessorElement)));
-    } else if (element27 is ExecutableElement) {
-      return recordType(node, ((element27 as ExecutableElement)).type);
-    } else if (element27 is PrefixElement) {
+    } else if (element31 is TypeVariableElement) {
+      return recordType(node, ((element31 as TypeVariableElement)).type);
+    } else if (element31 is FunctionTypeAliasElement) {
+      return recordType(node, ((element31 as FunctionTypeAliasElement)).type);
+    } else if (element31 is VariableElement) {
+      return recordType(node, ((element31 as VariableElement)).type);
+    } else if (element31 is MethodElement) {
+      return recordType(node, ((element31 as MethodElement)).type);
+    } else if (element31 is PropertyAccessorElement) {
+      return recordType(node, getType2((element31 as PropertyAccessorElement)));
+    } else if (element31 is ExecutableElement) {
+      return recordType(node, ((element31 as ExecutableElement)).type);
+    } else if (element31 is PrefixElement) {
       return null;
     } else {
       return recordType(node, _dynamicType);
@@ -4091,9 +4091,9 @@
         exceptionType = getType4(exceptionTypeName);
       }
       recordType(exception, exceptionType);
-      Element element28 = exception.element;
-      if (element28 is VariableElementImpl) {
-        ((element28 as VariableElementImpl)).type = exceptionType;
+      Element element32 = exception.element;
+      if (element32 is VariableElementImpl) {
+        ((element32 as VariableElementImpl)).type = exceptionType;
       } else {
       }
     }
@@ -4141,11 +4141,11 @@
   }
   Object visitConstructorDeclaration(ConstructorDeclaration node) {
     super.visitConstructorDeclaration(node);
-    ExecutableElementImpl element29 = node.element as ExecutableElementImpl;
-    FunctionTypeImpl type = new FunctionTypeImpl.con1(element29);
-    setTypeInformation(type, null, element29.parameters);
-    type.returnType = ((element29.enclosingElement as ClassElement)).type;
-    element29.type = type;
+    ExecutableElementImpl element33 = node.element as ExecutableElementImpl;
+    FunctionTypeImpl type = new FunctionTypeImpl.con1(element33);
+    setTypeInformation(type, null, element33.parameters);
+    type.returnType = ((element33.enclosingElement as ClassElement)).type;
+    element33.type = type;
     return null;
   }
   Object visitDeclaredIdentifier(DeclaredIdentifier node) {
@@ -4157,8 +4157,8 @@
     } else {
       declaredType = getType4(typeName);
     }
-    LocalVariableElementImpl element30 = node.element as LocalVariableElementImpl;
-    element30.type = declaredType;
+    LocalVariableElementImpl element34 = node.element as LocalVariableElementImpl;
+    element34.type = declaredType;
     return null;
   }
   Object visitDefaultFormalParameter(DefaultFormalParameter node) {
@@ -4167,9 +4167,9 @@
   }
   Object visitFieldFormalParameter(FieldFormalParameter node) {
     super.visitFieldFormalParameter(node);
-    Element element31 = node.identifier.element;
-    if (element31 is ParameterElementImpl) {
-      ParameterElementImpl parameter = element31 as ParameterElementImpl;
+    Element element35 = node.identifier.element;
+    if (element35 is ParameterElementImpl) {
+      ParameterElementImpl parameter = element35 as ParameterElementImpl;
       Type2 type;
       TypeName typeName = node.type;
       if (typeName == null) {
@@ -4184,35 +4184,35 @@
   }
   Object visitFunctionDeclaration(FunctionDeclaration node) {
     super.visitFunctionDeclaration(node);
-    ExecutableElementImpl element32 = node.element as ExecutableElementImpl;
-    FunctionTypeImpl type = new FunctionTypeImpl.con1(element32);
-    setTypeInformation(type, node.returnType, element32.parameters);
-    element32.type = type;
+    ExecutableElementImpl element36 = node.element as ExecutableElementImpl;
+    FunctionTypeImpl type = new FunctionTypeImpl.con1(element36);
+    setTypeInformation(type, node.returnType, element36.parameters);
+    element36.type = type;
     return null;
   }
   Object visitFunctionTypeAlias(FunctionTypeAlias node) {
     super.visitFunctionTypeAlias(node);
-    FunctionTypeAliasElementImpl element33 = node.element as FunctionTypeAliasElementImpl;
-    FunctionTypeImpl type18 = element33.type as FunctionTypeImpl;
-    setTypeInformation(type18, node.returnType, element33.parameters);
+    FunctionTypeAliasElementImpl element37 = node.element as FunctionTypeAliasElementImpl;
+    FunctionTypeImpl type18 = element37.type as FunctionTypeImpl;
+    setTypeInformation(type18, node.returnType, element37.parameters);
     return null;
   }
   Object visitFunctionTypedFormalParameter(FunctionTypedFormalParameter node) {
     super.visitFunctionTypedFormalParameter(node);
-    ParameterElementImpl element34 = node.identifier.element as ParameterElementImpl;
+    ParameterElementImpl element38 = node.identifier.element as ParameterElementImpl;
     FunctionTypeImpl type = new FunctionTypeImpl.con1((null as ExecutableElement));
     setTypeInformation(type, node.returnType, getElements(node.parameters));
-    element34.type = type;
+    element38.type = type;
     return null;
   }
   Object visitMethodDeclaration(MethodDeclaration node) {
     super.visitMethodDeclaration(node);
-    ExecutableElementImpl element35 = node.element as ExecutableElementImpl;
-    FunctionTypeImpl type = new FunctionTypeImpl.con1(element35);
-    setTypeInformation(type, node.returnType, element35.parameters);
-    element35.type = type;
-    if (element35 is PropertyAccessorElementImpl) {
-      PropertyAccessorElementImpl accessor = element35 as PropertyAccessorElementImpl;
+    ExecutableElementImpl element39 = node.element as ExecutableElementImpl;
+    FunctionTypeImpl type = new FunctionTypeImpl.con1(element39);
+    setTypeInformation(type, node.returnType, element39.parameters);
+    element39.type = type;
+    if (element39 is PropertyAccessorElementImpl) {
+      PropertyAccessorElementImpl accessor = element39 as PropertyAccessorElementImpl;
       PropertyInducingElementImpl variable5 = accessor.variable as PropertyInducingElementImpl;
       if (accessor.isGetter()) {
         variable5.type = type.returnType;
@@ -4234,9 +4234,9 @@
     } else {
       declaredType = getType4(typeName);
     }
-    Element element36 = node.identifier.element;
-    if (element36 is ParameterElement) {
-      ((element36 as ParameterElementImpl)).type = declaredType;
+    Element element40 = node.identifier.element;
+    if (element40 is ParameterElement) {
+      ((element40 as ParameterElementImpl)).type = declaredType;
     } else {
     }
     return null;
@@ -4359,11 +4359,11 @@
     } else {
       declaredType = getType4(typeName);
     }
-    Element element37 = node.name.element;
-    if (element37 is VariableElement) {
-      ((element37 as VariableElementImpl)).type = declaredType;
-      if (element37 is FieldElement) {
-        FieldElement field = element37 as FieldElement;
+    Element element41 = node.name.element;
+    if (element41 is VariableElement) {
+      ((element41 as VariableElementImpl)).type = declaredType;
+      if (element41 is FieldElement) {
+        FieldElement field = element41 as FieldElement;
         PropertyAccessorElementImpl getter5 = field.getter as PropertyAccessorElementImpl;
         FunctionTypeImpl getterType = new FunctionTypeImpl.con1(getter5);
         getterType.returnType = declaredType;
@@ -4389,11 +4389,11 @@
     if (identifier == null) {
       return null;
     }
-    Element element38 = identifier.element;
-    if (element38 is! ClassElementImpl) {
+    Element element42 = identifier.element;
+    if (element42 is! ClassElementImpl) {
       return null;
     }
-    return element38 as ClassElementImpl;
+    return element42 as ClassElementImpl;
   }
   /**
    * Return an array containing all of the elements associated with the parameters in the given
@@ -4404,9 +4404,9 @@
   List<ParameterElement> getElements(FormalParameterList parameterList) {
     List<ParameterElement> elements = new List<ParameterElement>();
     for (FormalParameter parameter in parameterList.parameters) {
-      ParameterElement element39 = parameter.identifier.element as ParameterElement;
-      if (element39 != null) {
-        elements.add(element39);
+      ParameterElement element43 = parameter.identifier.element as ParameterElement;
+      if (element43 != null) {
+        elements.add(element43);
       }
     }
     return new List.from(elements);
@@ -4562,13 +4562,13 @@
     }
     return new List.from(types);
   }
-  void setElement(Identifier typeName, Element element54) {
-    if (element54 != null) {
+  void setElement(Identifier typeName, Element element60) {
+    if (element60 != null) {
       if (typeName is SimpleIdentifier) {
-        ((typeName as SimpleIdentifier)).element = element54;
+        ((typeName as SimpleIdentifier)).element = element60;
       } else if (typeName is PrefixedIdentifier) {
         PrefixedIdentifier identifier = typeName as PrefixedIdentifier;
-        identifier.identifier.element = element54;
+        identifier.identifier.element = element60;
         SimpleIdentifier prefix9 = identifier.prefix;
         Element prefixElement = nameScope.lookup(prefix9, definingLibrary);
         if (prefixElement != null) {
@@ -4774,10 +4774,10 @@
    * @param onSwitchMember {@code true} if this label is associated with a {@code switch} member
    */
   LabelScope.con1(LabelScope outerScope, bool onSwitchStatement, bool onSwitchMember) {
-    _jtd_constructor_250_impl(outerScope, onSwitchStatement, onSwitchMember);
+    _jtd_constructor_254_impl(outerScope, onSwitchStatement, onSwitchMember);
   }
-  _jtd_constructor_250_impl(LabelScope outerScope, bool onSwitchStatement, bool onSwitchMember) {
-    _jtd_constructor_251_impl(outerScope, EMPTY_LABEL, new LabelElementImpl(_EMPTY_LABEL_IDENTIFIER, onSwitchStatement, onSwitchMember));
+  _jtd_constructor_254_impl(LabelScope outerScope, bool onSwitchStatement, bool onSwitchMember) {
+    _jtd_constructor_255_impl(outerScope, EMPTY_LABEL, new LabelElementImpl(_EMPTY_LABEL_IDENTIFIER, onSwitchStatement, onSwitchMember));
   }
   /**
    * Initialize a newly created scope to represent the given label.
@@ -4785,13 +4785,13 @@
    * @param label the label defined in this scope
    * @param element the element to which the label resolves
    */
-  LabelScope.con2(LabelScope outerScope2, String label4, LabelElement element19) {
-    _jtd_constructor_251_impl(outerScope2, label4, element19);
+  LabelScope.con2(LabelScope outerScope2, String label4, LabelElement element21) {
+    _jtd_constructor_255_impl(outerScope2, label4, element21);
   }
-  _jtd_constructor_251_impl(LabelScope outerScope2, String label4, LabelElement element19) {
+  _jtd_constructor_255_impl(LabelScope outerScope2, String label4, LabelElement element21) {
     this._outerScope = outerScope2;
     this._label = label4;
-    this._element = element19;
+    this._element = element21;
   }
   /**
    * Return the label element corresponding to the given label, or {@code null} if the given label
@@ -5037,7 +5037,9 @@
    * @param namespace the namespace containing the names to be added to this namespace
    */
   void addAll2(Map<String, Element> definedNames2, Namespace namespace) {
-    addAll(definedNames2, namespace.definedNames);
+    if (namespace != null) {
+      addAll(definedNames2, namespace.definedNames);
+    }
   }
   /**
    * Add the given element to the given mapping table if it has a publicly visible name.
@@ -5359,8 +5361,8 @@
     Expression initializer4 = node.initializer;
     if (initializer4 != null && node.isConst()) {
       EvaluationResultImpl result = validate(initializer4, CompileTimeErrorCode.CONST_INITIALIZED_WITH_NON_CONSTANT_VALUE);
-      VariableElementImpl element45 = node.element as VariableElementImpl;
-      element45.evaluationResult = result;
+      VariableElementImpl element49 = node.element as VariableElementImpl;
+      element49.evaluationResult = result;
     }
     return null;
   }
@@ -5400,8 +5402,8 @@
         if (defaultValue2 != null) {
           EvaluationResultImpl result = validate(defaultValue2, CompileTimeErrorCode.NON_CONSTANT_DEFAULT_VALUE);
           if (defaultParameter.isConst()) {
-            VariableElementImpl element46 = parameter.element as VariableElementImpl;
-            element46.evaluationResult = result;
+            VariableElementImpl element50 = parameter.element as VariableElementImpl;
+            element50.evaluationResult = result;
           }
         }
       }
@@ -5436,8 +5438,13 @@
    */
   bool _isEnclosingConstructorConst = false;
   /**
-   * The method or function that we are currently visiting, or {@code null} if we are not inside a
-   * method or function.
+   * This is set to <code>true</code> iff the visitor is currently visiting children nodes of a{@link CatchClause}.
+   * @see #visitCatchClause(CatchClause)
+   */
+  bool _isInCatchClause = false;
+  /**
+   * The method or function that we are currently visiting, or <code>null</code> if we are not
+   * inside a method or function.
    */
   ExecutableElement _currentFunction;
   /**
@@ -5449,6 +5456,7 @@
     this._currentLibrary = currentLibrary;
     this._typeProvider = typeProvider;
     _isEnclosingConstructorConst = false;
+    _isInCatchClause = false;
     _dynamicType = typeProvider.dynamicType;
     _DISALLOWED_TYPES_TO_EXTEND_OR_IMPLEMENT = <InterfaceType> [typeProvider.numType, typeProvider.intType, typeProvider.doubleType, typeProvider.boolType, typeProvider.stringType];
   }
@@ -5464,6 +5472,15 @@
     checkForInvalidAssignment(node);
     return super.visitAssignmentExpression(node);
   }
+  Object visitCatchClause(CatchClause node) {
+    bool previousIsInCatchClause = _isInCatchClause;
+    try {
+      _isInCatchClause = true;
+      return super.visitCatchClause(node);
+    } finally {
+      _isInCatchClause = previousIsInCatchClause;
+    }
+  }
   Object visitClassDeclaration(ClassDeclaration node) {
     checkForBuiltInIdentifierAsName(node.name, CompileTimeErrorCode.BUILT_IN_IDENTIFIER_AS_TYPE_NAME);
     return super.visitClassDeclaration(node);
@@ -5489,6 +5506,11 @@
       _currentFunction = previousFunction;
     }
   }
+  Object visitConstructorFieldInitializer(ConstructorFieldInitializer node) {
+    checkForFieldInitializedInInitializerAndDeclaration(node);
+    checkForFieldInitializedInParameterAndInitializer(node);
+    return super.visitConstructorFieldInitializer(node);
+  }
   Object visitDoStatement(DoStatement node) {
     checkForNonBoolCondition(node.condition);
     return super.visitDoStatement(node);
@@ -5499,6 +5521,7 @@
   }
   Object visitFieldFormalParameter(FieldFormalParameter node) {
     checkForConstFormalParameter(node);
+    checkForFieldInitializerOutsideConstructor(node);
     return super.visitFieldFormalParameter(node);
   }
   Object visitFunctionDeclaration(FunctionDeclaration node) {
@@ -5553,6 +5576,10 @@
       _currentFunction = previousFunction;
     }
   }
+  Object visitRethrowExpression(RethrowExpression node) {
+    checkForRethrowOutsideCatch(node);
+    return super.visitRethrowExpression(node);
+  }
   Object visitReturnStatement(ReturnStatement node) {
     checkForReturnOfInvalidType(node);
     return super.visitReturnStatement(node);
@@ -5589,8 +5616,8 @@
    */
   bool checkForArgumentDefinitionTestNonParameter(ArgumentDefinitionTest node) {
     SimpleIdentifier identifier14 = node.identifier;
-    Element element47 = identifier14.element;
-    if (element47 != null && element47 is! ParameterElement) {
+    Element element51 = identifier14.element;
+    if (element51 != null && element51 is! ParameterElement) {
       _errorReporter.reportError(CompileTimeErrorCode.ARGUMENT_DEFINITION_TEST_NON_PARAMETER, identifier14, [identifier14.name]);
       return true;
     }
@@ -5649,12 +5676,12 @@
     Expression expression16 = node.expression;
     Type2 type = expression16.staticType;
     if (type != null && type != _typeProvider.intType && type != _typeProvider.stringType) {
-      Element element48 = type.element;
-      if (element48 is ClassElement) {
-        ClassElement classElement = element48 as ClassElement;
+      Element element52 = type.element;
+      if (element52 is ClassElement) {
+        ClassElement classElement = element52 as ClassElement;
         MethodElement method = classElement.lookUpMethod("==", _currentLibrary);
         if (method != null && method.enclosingElement.type != _typeProvider.objectType) {
-          _errorReporter.reportError(CompileTimeErrorCode.CASE_EXPRESSION_TYPE_IMPLEMENTS_EQUALS, expression16, [element48.name]);
+          _errorReporter.reportError(CompileTimeErrorCode.CASE_EXPRESSION_TYPE_IMPLEMENTS_EQUALS, expression16, [element52.name]);
           return true;
         }
       }
@@ -5747,8 +5774,8 @@
    */
   bool checkForConstOrNewWithAbstractClass(InstanceCreationExpression node, TypeName typeName, InterfaceType type) {
     if (type.element.isAbstract()) {
-      ConstructorElement element49 = node.element;
-      if (element49 != null && !element49.isFactory()) {
+      ConstructorElement element53 = node.element;
+      if (element53 != null && !element53.isFactory()) {
         if (identical(((node.keyword as sc.KeywordToken)).keyword, sc.Keyword.CONST)) {
           _errorReporter.reportError(StaticWarningCode.CONST_WITH_ABSTRACT_CLASS, typeName, []);
         } else {
@@ -5836,6 +5863,69 @@
     return false;
   }
   /**
+   * This verifies that the passed constructor field initializer is not also a final variable that
+   * already included an initialization.
+   * @param node the constructor field initializer to test
+   * @return return <code>true</code> if and only if an error code is generated on the passed node
+   * @see CompileTimeErrorCode#FIELD_INITIALIZED_IN_INITIALIZER_AND_DECLARATION
+   */
+  bool checkForFieldInitializedInInitializerAndDeclaration(ConstructorFieldInitializer node) {
+    SimpleIdentifier identifier = node.fieldName;
+    Element element54 = identifier.element;
+    if (element54 is PropertyAccessorElement) {
+      PropertyAccessorElement propertyAccessorElement = element54 as PropertyAccessorElement;
+      PropertyInducingElement propertyInducingElement = propertyAccessorElement.variable;
+      if (propertyInducingElement.initializer != null && (propertyInducingElement.isFinal() || propertyInducingElement.isConst())) {
+        _errorReporter.reportError(CompileTimeErrorCode.FIELD_INITIALIZED_IN_INITIALIZER_AND_DECLARATION, node, []);
+        return true;
+      }
+    }
+    return false;
+  }
+  /**
+   * This verifies that the passed constructor field initializer is not also a field formal
+   * parameter in the constructor declaration.
+   * @param node the constructor field initializer to test
+   * @return return <code>true</code> if and only if an error code is generated on the passed node
+   * @see CompileTimeErrorCode#FIELD_INITIALIZED_IN_PARAMETER_AND_INITIALIZER
+   */
+  bool checkForFieldInitializedInParameterAndInitializer(ConstructorFieldInitializer node) {
+    SimpleIdentifier identifier = node.fieldName;
+    Element element55 = identifier.element;
+    ASTNode parent18 = node.parent;
+    if (element55 != null && parent18 is ConstructorDeclaration) {
+      ConstructorDeclaration constructorDeclaration = parent18 as ConstructorDeclaration;
+      NodeList<FormalParameter> formalParameters = constructorDeclaration.parameters.parameters;
+      for (FormalParameter formalParameter in formalParameters) {
+        if (formalParameter is FieldFormalParameter) {
+          FieldFormalParameter fieldFormalParameter = formalParameter as FieldFormalParameter;
+          if (fieldFormalParameter.identifier.name == element55.name) {
+            _errorReporter.reportError(CompileTimeErrorCode.FIELD_INITIALIZED_IN_PARAMETER_AND_INITIALIZER, node, []);
+            return true;
+          }
+        }
+      }
+    }
+    return false;
+  }
+  /**
+   * This verifies that the passed field formal parameter is in a constructor declaration.
+   * @param node the field formal parameter to test
+   * @return return <code>true</code> if and only if an error code is generated on the passed node
+   * @see CompileTimeErrorCode#FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR
+   */
+  bool checkForFieldInitializerOutsideConstructor(FieldFormalParameter node) {
+    ASTNode parent19 = node.parent;
+    if (parent19 != null) {
+      ASTNode grandparent = parent19.parent;
+      if (grandparent != null && grandparent is! ConstructorDeclaration && grandparent.parent is! ConstructorDeclaration) {
+        _errorReporter.reportError(CompileTimeErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR, node, []);
+        return true;
+      }
+    }
+    return false;
+  }
+  /**
    * This verifies that the passed implements clause does not implement classes such as 'num' or
    * 'String'.
    * @param node the implements clause to test
@@ -5906,6 +5996,19 @@
     return false;
   }
   /**
+   * This checks that the rethrow is inside of a catch clause.
+   * @param node the rethrow expression to evaluate
+   * @return <code>true</code> if and only if an error code is generated on the passed node
+   * @see CompileTimeErrorCode#RETHROW_OUTSIDE_CATCH
+   */
+  bool checkForRethrowOutsideCatch(RethrowExpression node) {
+    if (!_isInCatchClause) {
+      _errorReporter.reportError(CompileTimeErrorCode.RETHROW_OUTSIDE_CATCH, node, []);
+      return true;
+    }
+    return false;
+  }
+  /**
    * This checks that the return type matches the type of the declared return type in the enclosing
    * method or function.
    * @param node the return statement to evaluate
diff --git a/pkg/analyzer_experimental/lib/src/generated/scanner.dart b/pkg/analyzer_experimental/lib/src/generated/scanner.dart
index 9afb79d..5ad4162 100644
--- a/pkg/analyzer_experimental/lib/src/generated/scanner.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/scanner.dart
@@ -185,43 +185,45 @@
   static final Keyword DEFAULT = new Keyword.con1('DEFAULT', 7, "default");
   static final Keyword DO = new Keyword.con1('DO', 8, "do");
   static final Keyword ELSE = new Keyword.con1('ELSE', 9, "else");
-  static final Keyword EXTENDS = new Keyword.con1('EXTENDS', 10, "extends");
-  static final Keyword FALSE = new Keyword.con1('FALSE', 11, "false");
-  static final Keyword FINAL = new Keyword.con1('FINAL', 12, "final");
-  static final Keyword FINALLY = new Keyword.con1('FINALLY', 13, "finally");
-  static final Keyword FOR = new Keyword.con1('FOR', 14, "for");
-  static final Keyword IF = new Keyword.con1('IF', 15, "if");
-  static final Keyword IN = new Keyword.con1('IN', 16, "in");
-  static final Keyword IS = new Keyword.con1('IS', 17, "is");
-  static final Keyword NEW = new Keyword.con1('NEW', 18, "new");
-  static final Keyword NULL = new Keyword.con1('NULL', 19, "null");
-  static final Keyword RETURN = new Keyword.con1('RETURN', 20, "return");
-  static final Keyword SUPER = new Keyword.con1('SUPER', 21, "super");
-  static final Keyword SWITCH = new Keyword.con1('SWITCH', 22, "switch");
-  static final Keyword THIS = new Keyword.con1('THIS', 23, "this");
-  static final Keyword THROW = new Keyword.con1('THROW', 24, "throw");
-  static final Keyword TRUE = new Keyword.con1('TRUE', 25, "true");
-  static final Keyword TRY = new Keyword.con1('TRY', 26, "try");
-  static final Keyword VAR = new Keyword.con1('VAR', 27, "var");
-  static final Keyword VOID = new Keyword.con1('VOID', 28, "void");
-  static final Keyword WHILE = new Keyword.con1('WHILE', 29, "while");
-  static final Keyword WITH = new Keyword.con1('WITH', 30, "with");
-  static final Keyword ABSTRACT = new Keyword.con2('ABSTRACT', 31, "abstract", true);
-  static final Keyword AS = new Keyword.con2('AS', 32, "as", true);
-  static final Keyword DYNAMIC = new Keyword.con2('DYNAMIC', 33, "dynamic", true);
-  static final Keyword EXPORT = new Keyword.con2('EXPORT', 34, "export", true);
-  static final Keyword EXTERNAL = new Keyword.con2('EXTERNAL', 35, "external", true);
-  static final Keyword FACTORY = new Keyword.con2('FACTORY', 36, "factory", true);
-  static final Keyword GET = new Keyword.con2('GET', 37, "get", true);
-  static final Keyword IMPLEMENTS = new Keyword.con2('IMPLEMENTS', 38, "implements", true);
-  static final Keyword IMPORT = new Keyword.con2('IMPORT', 39, "import", true);
-  static final Keyword LIBRARY = new Keyword.con2('LIBRARY', 40, "library", true);
-  static final Keyword OPERATOR = new Keyword.con2('OPERATOR', 41, "operator", true);
-  static final Keyword PART = new Keyword.con2('PART', 42, "part", true);
-  static final Keyword SET = new Keyword.con2('SET', 43, "set", true);
-  static final Keyword STATIC = new Keyword.con2('STATIC', 44, "static", true);
-  static final Keyword TYPEDEF = new Keyword.con2('TYPEDEF', 45, "typedef", true);
-  static final List<Keyword> values = [ASSERT, BREAK, CASE, CATCH, CLASS, CONST, CONTINUE, DEFAULT, DO, ELSE, EXTENDS, FALSE, FINAL, FINALLY, FOR, IF, IN, IS, NEW, NULL, RETURN, SUPER, SWITCH, THIS, THROW, TRUE, TRY, VAR, VOID, WHILE, WITH, ABSTRACT, AS, DYNAMIC, EXPORT, EXTERNAL, FACTORY, GET, IMPLEMENTS, IMPORT, LIBRARY, OPERATOR, PART, SET, STATIC, TYPEDEF];
+  static final Keyword ENUM = new Keyword.con1('ENUM', 10, "enum");
+  static final Keyword EXTENDS = new Keyword.con1('EXTENDS', 11, "extends");
+  static final Keyword FALSE = new Keyword.con1('FALSE', 12, "false");
+  static final Keyword FINAL = new Keyword.con1('FINAL', 13, "final");
+  static final Keyword FINALLY = new Keyword.con1('FINALLY', 14, "finally");
+  static final Keyword FOR = new Keyword.con1('FOR', 15, "for");
+  static final Keyword IF = new Keyword.con1('IF', 16, "if");
+  static final Keyword IN = new Keyword.con1('IN', 17, "in");
+  static final Keyword IS = new Keyword.con1('IS', 18, "is");
+  static final Keyword NEW = new Keyword.con1('NEW', 19, "new");
+  static final Keyword NULL = new Keyword.con1('NULL', 20, "null");
+  static final Keyword RETHROW = new Keyword.con1('RETHROW', 21, "rethrow");
+  static final Keyword RETURN = new Keyword.con1('RETURN', 22, "return");
+  static final Keyword SUPER = new Keyword.con1('SUPER', 23, "super");
+  static final Keyword SWITCH = new Keyword.con1('SWITCH', 24, "switch");
+  static final Keyword THIS = new Keyword.con1('THIS', 25, "this");
+  static final Keyword THROW = new Keyword.con1('THROW', 26, "throw");
+  static final Keyword TRUE = new Keyword.con1('TRUE', 27, "true");
+  static final Keyword TRY = new Keyword.con1('TRY', 28, "try");
+  static final Keyword VAR = new Keyword.con1('VAR', 29, "var");
+  static final Keyword VOID = new Keyword.con1('VOID', 30, "void");
+  static final Keyword WHILE = new Keyword.con1('WHILE', 31, "while");
+  static final Keyword WITH = new Keyword.con1('WITH', 32, "with");
+  static final Keyword ABSTRACT = new Keyword.con2('ABSTRACT', 33, "abstract", true);
+  static final Keyword AS = new Keyword.con2('AS', 34, "as", true);
+  static final Keyword DYNAMIC = new Keyword.con2('DYNAMIC', 35, "dynamic", true);
+  static final Keyword EXPORT = new Keyword.con2('EXPORT', 36, "export", true);
+  static final Keyword EXTERNAL = new Keyword.con2('EXTERNAL', 37, "external", true);
+  static final Keyword FACTORY = new Keyword.con2('FACTORY', 38, "factory", true);
+  static final Keyword GET = new Keyword.con2('GET', 39, "get", true);
+  static final Keyword IMPLEMENTS = new Keyword.con2('IMPLEMENTS', 40, "implements", true);
+  static final Keyword IMPORT = new Keyword.con2('IMPORT', 41, "import", true);
+  static final Keyword LIBRARY = new Keyword.con2('LIBRARY', 42, "library", true);
+  static final Keyword OPERATOR = new Keyword.con2('OPERATOR', 43, "operator", true);
+  static final Keyword PART = new Keyword.con2('PART', 44, "part", true);
+  static final Keyword SET = new Keyword.con2('SET', 45, "set", true);
+  static final Keyword STATIC = new Keyword.con2('STATIC', 46, "static", true);
+  static final Keyword TYPEDEF = new Keyword.con2('TYPEDEF', 47, "typedef", true);
+  static final List<Keyword> values = [ASSERT, BREAK, CASE, CATCH, CLASS, CONST, CONTINUE, DEFAULT, DO, ELSE, ENUM, EXTENDS, FALSE, FINAL, FINALLY, FOR, IF, IN, IS, NEW, NULL, RETHROW, RETURN, SUPER, SWITCH, THIS, THROW, TRUE, TRY, VAR, VOID, WHILE, WITH, ABSTRACT, AS, DYNAMIC, EXPORT, EXTERNAL, FACTORY, GET, IMPLEMENTS, IMPORT, LIBRARY, OPERATOR, PART, SET, STATIC, TYPEDEF];
   String __name;
   int __ordinal = 0;
   int get ordinal => __ordinal;
@@ -255,10 +257,10 @@
    * @param syntax the lexeme for the keyword
    */
   Keyword.con1(String ___name, int ___ordinal, String syntax) {
-    _jtd_constructor_278_impl(___name, ___ordinal, syntax);
+    _jtd_constructor_282_impl(___name, ___ordinal, syntax);
   }
-  _jtd_constructor_278_impl(String ___name, int ___ordinal, String syntax) {
-    _jtd_constructor_279_impl(___name, ___ordinal, syntax, false);
+  _jtd_constructor_282_impl(String ___name, int ___ordinal, String syntax) {
+    _jtd_constructor_283_impl(___name, ___ordinal, syntax, false);
   }
   /**
    * Initialize a newly created keyword to have the given syntax. The keyword is a pseudo-keyword if
@@ -267,9 +269,9 @@
    * @param isPseudoKeyword {@code true} if this keyword is a pseudo-keyword
    */
   Keyword.con2(String ___name, int ___ordinal, String syntax2, bool isPseudoKeyword) {
-    _jtd_constructor_279_impl(___name, ___ordinal, syntax2, isPseudoKeyword);
+    _jtd_constructor_283_impl(___name, ___ordinal, syntax2, isPseudoKeyword);
   }
-  _jtd_constructor_279_impl(String ___name, int ___ordinal, String syntax2, bool isPseudoKeyword) {
+  _jtd_constructor_283_impl(String ___name, int ___ordinal, String syntax2, bool isPseudoKeyword) {
     __name = ___name;
     __ordinal = ___ordinal;
     this._syntax = syntax2;
@@ -1258,7 +1260,7 @@
     }
     return _buffer.charAt(++_charOffset);
   }
-  String getString(int start, int endDelta) => _buffer.subSequence(start, _charOffset + 1 + endDelta).toString();
+  String getString(int start, int endDelta) => ((_buffer as CharSequence)).subSequence(start, _charOffset + 1 + endDelta).toString();
   int peek() {
     if (_charOffset + 1 >= _buffer.length()) {
       return -1;
@@ -1654,15 +1656,15 @@
    */
   int _precedence = 0;
   TokenClass.con1(String ___name, int ___ordinal) {
-    _jtd_constructor_288_impl(___name, ___ordinal);
+    _jtd_constructor_292_impl(___name, ___ordinal);
   }
-  _jtd_constructor_288_impl(String ___name, int ___ordinal) {
-    _jtd_constructor_289_impl(___name, ___ordinal, 0);
+  _jtd_constructor_292_impl(String ___name, int ___ordinal) {
+    _jtd_constructor_293_impl(___name, ___ordinal, 0);
   }
   TokenClass.con2(String ___name, int ___ordinal, int precedence2) {
-    _jtd_constructor_289_impl(___name, ___ordinal, precedence2);
+    _jtd_constructor_293_impl(___name, ___ordinal, precedence2);
   }
-  _jtd_constructor_289_impl(String ___name, int ___ordinal, int precedence2) {
+  _jtd_constructor_293_impl(String ___name, int ___ordinal, int precedence2) {
     __name = ___name;
     __ordinal = ___ordinal;
     this._precedence = precedence2;
@@ -1788,15 +1790,15 @@
    */
   String _lexeme;
   TokenType.con1(String ___name, int ___ordinal) {
-    _jtd_constructor_290_impl(___name, ___ordinal);
+    _jtd_constructor_294_impl(___name, ___ordinal);
   }
-  _jtd_constructor_290_impl(String ___name, int ___ordinal) {
-    _jtd_constructor_291_impl(___name, ___ordinal, TokenClass.NO_CLASS, null);
+  _jtd_constructor_294_impl(String ___name, int ___ordinal) {
+    _jtd_constructor_295_impl(___name, ___ordinal, TokenClass.NO_CLASS, null);
   }
   TokenType.con2(String ___name, int ___ordinal, TokenClass tokenClass2, String lexeme2) {
-    _jtd_constructor_291_impl(___name, ___ordinal, tokenClass2, lexeme2);
+    _jtd_constructor_295_impl(___name, ___ordinal, tokenClass2, lexeme2);
   }
-  _jtd_constructor_291_impl(String ___name, int ___ordinal, TokenClass tokenClass2, String lexeme2) {
+  _jtd_constructor_295_impl(String ___name, int ___ordinal, TokenClass tokenClass2, String lexeme2) {
     __name = ___name;
     __ordinal = ___ordinal;
     this._tokenClass = tokenClass2 == null ? TokenClass.NO_CLASS : tokenClass2;
diff --git a/pkg/analyzer_experimental/lib/src/generated/sdk.dart b/pkg/analyzer_experimental/lib/src/generated/sdk.dart
index 116f6ed..758a694 100644
--- a/pkg/analyzer_experimental/lib/src/generated/sdk.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/sdk.dart
@@ -9,11 +9,11 @@
 import 'java_io.dart';
 import 'java_engine.dart';
 import 'java_engine_io.dart';
-import 'package:analyzer_experimental/src/generated/source_io.dart';
-import 'package:analyzer_experimental/src/generated/error.dart';
-import 'package:analyzer_experimental/src/generated/scanner.dart';
-import 'package:analyzer_experimental/src/generated/parser.dart';
-import 'package:analyzer_experimental/src/generated/ast.dart';
+import 'source_io.dart';
+import 'error.dart';
+import 'scanner.dart';
+import 'parser.dart';
+import 'ast.dart';
 import 'package:analyzer_experimental/src/generated/engine.dart' show AnalysisEngine;
 
 /**
@@ -195,7 +195,7 @@
    */
   LibraryMap readFrom(JavaFile librariesFile, String libraryFileContents) {
     List<bool> foundError = [false];
-    AnalysisErrorListener errorListener = new AnalysisErrorListener_6(foundError);
+    AnalysisErrorListener errorListener = new AnalysisErrorListener_7(foundError);
     Source source = new FileBasedSource.con2(null, librariesFile, false);
     StringScanner scanner = new StringScanner(source, libraryFileContents, errorListener);
     Parser parser = new Parser(source, errorListener);
@@ -286,9 +286,9 @@
     return null;
   }
 }
-class AnalysisErrorListener_6 implements AnalysisErrorListener {
+class AnalysisErrorListener_7 implements AnalysisErrorListener {
   List<bool> foundError;
-  AnalysisErrorListener_6(this.foundError);
+  AnalysisErrorListener_7(this.foundError);
   void onError(AnalysisError error) {
     foundError[0] = true;
   }
@@ -656,7 +656,7 @@
       JavaFile librariesFile = new JavaFile.relative(new JavaFile.relative(libraryDirectory, _INTERNAL_DIR), _LIBRARIES_FILE);
       String contents = librariesFile.readAsStringSync();
       _libraryMap = new SdkLibrariesReader().readFrom(librariesFile, contents);
-    } on JavaException catch (exception) {
+    } catch (exception) {
       AnalysisEngine.instance.logger.logError3(exception);
       _libraryMap = new LibraryMap();
     }
diff --git a/pkg/analyzer_experimental/lib/src/generated/source.dart b/pkg/analyzer_experimental/lib/src/generated/source.dart
index 9c5ca55..c7db991 100644
--- a/pkg/analyzer_experimental/lib/src/generated/source.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/source.dart
@@ -30,9 +30,9 @@
    * @param resolvers the resolvers used to resolve absolute URI's
    */
   SourceFactory.con1(ContentCache contentCache2, List<UriResolver> resolvers2) {
-    _jtd_constructor_302_impl(contentCache2, resolvers2);
+    _jtd_constructor_306_impl(contentCache2, resolvers2);
   }
-  _jtd_constructor_302_impl(ContentCache contentCache2, List<UriResolver> resolvers2) {
+  _jtd_constructor_306_impl(ContentCache contentCache2, List<UriResolver> resolvers2) {
     this._contentCache = contentCache2;
     this._resolvers = resolvers2;
   }
@@ -41,10 +41,10 @@
    * @param resolvers the resolvers used to resolve absolute URI's
    */
   SourceFactory.con2(List<UriResolver> resolvers) {
-    _jtd_constructor_303_impl(resolvers);
+    _jtd_constructor_307_impl(resolvers);
   }
-  _jtd_constructor_303_impl(List<UriResolver> resolvers) {
-    _jtd_constructor_302_impl(new ContentCache(), resolvers);
+  _jtd_constructor_307_impl(List<UriResolver> resolvers) {
+    _jtd_constructor_306_impl(new ContentCache(), resolvers);
   }
   /**
    * Return a source object representing the given absolute URI, or {@code null} if the URI is not a
diff --git a/pkg/analyzer_experimental/lib/src/generated/source_io.dart b/pkg/analyzer_experimental/lib/src/generated/source_io.dart
index 470a12b..a31152a 100644
--- a/pkg/analyzer_experimental/lib/src/generated/source_io.dart
+++ b/pkg/analyzer_experimental/lib/src/generated/source_io.dart
@@ -37,10 +37,10 @@
    * @param file the file represented by this source
    */
   FileBasedSource.con1(SourceFactory factory, JavaFile file) {
-    _jtd_constructor_298_impl(factory, file);
+    _jtd_constructor_302_impl(factory, file);
   }
-  _jtd_constructor_298_impl(SourceFactory factory, JavaFile file) {
-    _jtd_constructor_299_impl(factory, file, false);
+  _jtd_constructor_302_impl(SourceFactory factory, JavaFile file) {
+    _jtd_constructor_303_impl(factory, file, false);
   }
   /**
    * Initialize a newly created source object.
@@ -49,16 +49,15 @@
    * @param inSystemLibrary {@code true} if this source is in one of the system libraries
    */
   FileBasedSource.con2(SourceFactory factory2, JavaFile file3, bool inSystemLibrary2) {
-    _jtd_constructor_299_impl(factory2, file3, inSystemLibrary2);
+    _jtd_constructor_303_impl(factory2, file3, inSystemLibrary2);
   }
-  _jtd_constructor_299_impl(SourceFactory factory2, JavaFile file3, bool inSystemLibrary2) {
+  _jtd_constructor_303_impl(SourceFactory factory2, JavaFile file3, bool inSystemLibrary2) {
     this._factory = factory2;
     this._file = file3;
     this._inSystemLibrary = inSystemLibrary2;
   }
   bool operator ==(Object object) => object != null && identical(this.runtimeType, object.runtimeType) && _file == ((object as FileBasedSource))._file;
-  bool exists() => _file.exists();
-  AnalysisContext get context => _factory.context;
+  bool exists() => _factory.getContents(this) != null || (_file.exists() && !_file.isDirectory());
   void getContents(Source_ContentReceiver receiver) {
     {
       String contents = _factory.getContents(this);
@@ -69,6 +68,7 @@
     }
     receiver.accept2(_file.readAsStringSync());
   }
+  AnalysisContext get context => _factory.context;
   String get encoding => _file.toURI().toString();
   String get fullName => _file.getAbsolutePath();
   int get modificationStamp {
@@ -86,7 +86,7 @@
     try {
       Uri resolvedUri = file.toURI().resolveUri(containedUri);
       return new FileBasedSource.con1(_factory, new JavaFile.fromUri(resolvedUri));
-    } on JavaException catch (exception) {
+    } catch (exception) {
     }
     return null;
   }
@@ -221,19 +221,19 @@
    * @param directory the directory (not {@code null})
    */
   DirectoryBasedSourceContainer.con1(JavaFile directory) {
-    _jtd_constructor_296_impl(directory);
+    _jtd_constructor_300_impl(directory);
   }
-  _jtd_constructor_296_impl(JavaFile directory) {
-    _jtd_constructor_297_impl(directory.getPath());
+  _jtd_constructor_300_impl(JavaFile directory) {
+    _jtd_constructor_301_impl(directory.getPath());
   }
   /**
    * Construct a container representing the specified path and containing any sources whose{@link Source#getFullName()} starts with the specified path.
    * @param path the path (not {@code null} and not empty)
    */
   DirectoryBasedSourceContainer.con2(String path3) {
-    _jtd_constructor_297_impl(path3);
+    _jtd_constructor_301_impl(path3);
   }
-  _jtd_constructor_297_impl(String path3) {
+  _jtd_constructor_301_impl(String path3) {
     this._path = appendFileSeparator(path3);
   }
   bool contains(Source source) => source.fullName.startsWith(_path);
diff --git a/pkg/analyzer_experimental/test/generated/ast_test.dart b/pkg/analyzer_experimental/test/generated/ast_test.dart
index fec113d..c927106 100644
--- a/pkg/analyzer_experimental/test/generated/ast_test.dart
+++ b/pkg/analyzer_experimental/test/generated/ast_test.dart
@@ -356,11 +356,11 @@
    * @param element the element defining the type represented by the type name
    * @return the type name that was created
    */
-  static TypeName typeName(ClassElement element55, List<TypeName> arguments) {
-    SimpleIdentifier name22 = identifier2(element55.name);
-    name22.element = element55;
+  static TypeName typeName(ClassElement element61, List<TypeName> arguments) {
+    SimpleIdentifier name22 = identifier2(element61.name);
+    name22.element = element61;
     TypeName typeName = typeName2(name22, arguments);
-    typeName.type = element55.type;
+    typeName.type = element61.type;
     return typeName;
   }
   static TypeName typeName2(Identifier name, List<TypeName> arguments) {
@@ -386,7 +386,7 @@
   }
   static VariableDeclaration variableDeclaration(String name) => new VariableDeclaration.full(null, null, identifier2(name), null, null);
   static VariableDeclaration variableDeclaration2(String name, Expression initializer) => new VariableDeclaration.full(null, null, identifier2(name), TokenFactory.token3(TokenType.EQ), initializer);
-  static VariableDeclarationList variableDeclarationList(Keyword keyword, TypeName type, List<VariableDeclaration> variables) => new VariableDeclarationList.full(keyword == null ? null : TokenFactory.token(keyword), type, list(variables));
+  static VariableDeclarationList variableDeclarationList(Keyword keyword, TypeName type, List<VariableDeclaration> variables) => new VariableDeclarationList.full(null, null, keyword == null ? null : TokenFactory.token(keyword), type, list(variables));
   static VariableDeclarationList variableDeclarationList2(Keyword keyword, List<VariableDeclaration> variables) => variableDeclarationList(keyword, null, variables);
   static VariableDeclarationStatement variableDeclarationStatement(Keyword keyword, TypeName type, List<VariableDeclaration> variables) => new VariableDeclarationStatement.full(variableDeclarationList(keyword, type, variables), TokenFactory.token3(TokenType.SEMICOLON));
   static VariableDeclarationStatement variableDeclarationStatement2(Keyword keyword, List<VariableDeclaration> variables) => variableDeclarationStatement(keyword, null, variables);
@@ -542,10 +542,10 @@
    */
   ASTNode topMostNode(SimpleIdentifier identifier) {
     ASTNode child = identifier;
-    ASTNode parent18 = identifier.parent;
-    while (parent18 != null) {
-      child = parent18;
-      parent18 = parent18.parent;
+    ASTNode parent20 = identifier.parent;
+    while (parent20 != null) {
+      child = parent20;
+      parent20 = parent20.parent;
     }
     return child;
   }
diff --git a/pkg/analyzer_experimental/test/generated/element_test.dart b/pkg/analyzer_experimental/test/generated/element_test.dart
index 62f3f6e..edfa3a3 100644
--- a/pkg/analyzer_experimental/test/generated/element_test.dart
+++ b/pkg/analyzer_experimental/test/generated/element_test.dart
@@ -50,11 +50,11 @@
   void test_getComponents() {
     String encoding = "a;b;c";
     ElementLocationImpl location = new ElementLocationImpl.con2(encoding);
-    List<String> components2 = location.components;
-    EngineTestCase.assertLength(3, components2);
-    JUnitTestCase.assertEquals("a", components2[0]);
-    JUnitTestCase.assertEquals("b", components2[1]);
-    JUnitTestCase.assertEquals("c", components2[2]);
+    List<String> components3 = location.components;
+    EngineTestCase.assertLength(3, components3);
+    JUnitTestCase.assertEquals("a", components3[0]);
+    JUnitTestCase.assertEquals("b", components3[1]);
+    JUnitTestCase.assertEquals("c", components3[2]);
   }
   void test_getEncoding() {
     String encoding = "a;b;c;;d";
@@ -1484,7 +1484,7 @@
   }
   void test_isSubtypeOf_baseCase_classFunction() {
     ClassElementImpl functionElement = ElementFactory.classElement2("Function", []);
-    InterfaceTypeImpl functionType = new InterfaceTypeImpl_12(functionElement);
+    InterfaceTypeImpl functionType = new InterfaceTypeImpl_14(functionElement);
     FunctionType f = ElementFactory.functionElement("f").type;
     JUnitTestCase.assertTrue(f.isSubtypeOf(functionType));
   }
@@ -1896,8 +1896,8 @@
     });
   }
 }
-class InterfaceTypeImpl_12 extends InterfaceTypeImpl {
-  InterfaceTypeImpl_12(ClassElement arg0) : super.con1(arg0);
+class InterfaceTypeImpl_14 extends InterfaceTypeImpl {
+  InterfaceTypeImpl_14(ClassElement arg0) : super.con1(arg0);
   bool isDartCoreFunction() => true;
 }
 main() {
diff --git a/pkg/analyzer_experimental/test/generated/parser_test.dart b/pkg/analyzer_experimental/test/generated/parser_test.dart
index 01613ab..3244f2b 100644
--- a/pkg/analyzer_experimental/test/generated/parser_test.dart
+++ b/pkg/analyzer_experimental/test/generated/parser_test.dart
@@ -200,21 +200,21 @@
     JUnitTestCase.assertFalse(isSwitchMember("break;"));
   }
   void test_parseAdditiveExpression_normal() {
-    BinaryExpression expression = ParserTestCase.parse6("parseAdditiveExpression", "x + y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseAdditiveExpression", "x + y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.PLUS, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseAdditiveExpression_super() {
-    BinaryExpression expression = ParserTestCase.parse6("parseAdditiveExpression", "super + y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseAdditiveExpression", "super + y", []);
     EngineTestCase.assertInstanceOf(SuperExpression, expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.PLUS, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseAnnotation_n1() {
-    Annotation annotation = ParserTestCase.parse6("parseAnnotation", "@A", []);
+    Annotation annotation = ParserTestCase.parse5("parseAnnotation", "@A", []);
     JUnitTestCase.assertNotNull(annotation.atSign);
     JUnitTestCase.assertNotNull(annotation.name);
     JUnitTestCase.assertNull(annotation.period);
@@ -222,7 +222,7 @@
     JUnitTestCase.assertNull(annotation.arguments);
   }
   void test_parseAnnotation_n1_a() {
-    Annotation annotation = ParserTestCase.parse6("parseAnnotation", "@A(x,y)", []);
+    Annotation annotation = ParserTestCase.parse5("parseAnnotation", "@A(x,y)", []);
     JUnitTestCase.assertNotNull(annotation.atSign);
     JUnitTestCase.assertNotNull(annotation.name);
     JUnitTestCase.assertNull(annotation.period);
@@ -230,7 +230,7 @@
     JUnitTestCase.assertNotNull(annotation.arguments);
   }
   void test_parseAnnotation_n2() {
-    Annotation annotation = ParserTestCase.parse6("parseAnnotation", "@A.B", []);
+    Annotation annotation = ParserTestCase.parse5("parseAnnotation", "@A.B", []);
     JUnitTestCase.assertNotNull(annotation.atSign);
     JUnitTestCase.assertNotNull(annotation.name);
     JUnitTestCase.assertNull(annotation.period);
@@ -238,7 +238,7 @@
     JUnitTestCase.assertNull(annotation.arguments);
   }
   void test_parseAnnotation_n2_a() {
-    Annotation annotation = ParserTestCase.parse6("parseAnnotation", "@A.B(x,y)", []);
+    Annotation annotation = ParserTestCase.parse5("parseAnnotation", "@A.B(x,y)", []);
     JUnitTestCase.assertNotNull(annotation.atSign);
     JUnitTestCase.assertNotNull(annotation.name);
     JUnitTestCase.assertNull(annotation.period);
@@ -246,7 +246,7 @@
     JUnitTestCase.assertNotNull(annotation.arguments);
   }
   void test_parseAnnotation_n3() {
-    Annotation annotation = ParserTestCase.parse6("parseAnnotation", "@A.B.C", []);
+    Annotation annotation = ParserTestCase.parse5("parseAnnotation", "@A.B.C", []);
     JUnitTestCase.assertNotNull(annotation.atSign);
     JUnitTestCase.assertNotNull(annotation.name);
     JUnitTestCase.assertNotNull(annotation.period);
@@ -254,7 +254,7 @@
     JUnitTestCase.assertNull(annotation.arguments);
   }
   void test_parseAnnotation_n3_a() {
-    Annotation annotation = ParserTestCase.parse6("parseAnnotation", "@A.B.C(x,y)", []);
+    Annotation annotation = ParserTestCase.parse5("parseAnnotation", "@A.B.C(x,y)", []);
     JUnitTestCase.assertNotNull(annotation.atSign);
     JUnitTestCase.assertNotNull(annotation.name);
     JUnitTestCase.assertNotNull(annotation.period);
@@ -262,7 +262,7 @@
     JUnitTestCase.assertNotNull(annotation.arguments);
   }
   void test_parseArgument_named() {
-    NamedExpression expression = ParserTestCase.parse6("parseArgument", "n: x", []);
+    NamedExpression expression = ParserTestCase.parse5("parseArgument", "n: x", []);
     Label name23 = expression.name;
     JUnitTestCase.assertNotNull(name23);
     JUnitTestCase.assertNotNull(name23.label);
@@ -271,36 +271,36 @@
   }
   void test_parseArgument_unnamed() {
     String lexeme = "x";
-    SimpleIdentifier identifier = ParserTestCase.parse6("parseArgument", lexeme, []);
+    SimpleIdentifier identifier = ParserTestCase.parse5("parseArgument", lexeme, []);
     JUnitTestCase.assertEquals(lexeme, identifier.name);
   }
   void test_parseArgumentDefinitionTest() {
-    ArgumentDefinitionTest test = ParserTestCase.parse6("parseArgumentDefinitionTest", "?x", []);
+    ArgumentDefinitionTest test = ParserTestCase.parse5("parseArgumentDefinitionTest", "?x", []);
     JUnitTestCase.assertNotNull(test.question);
     JUnitTestCase.assertNotNull(test.identifier);
   }
   void test_parseArgumentList_empty() {
-    ArgumentList argumentList = ParserTestCase.parse6("parseArgumentList", "()", []);
+    ArgumentList argumentList = ParserTestCase.parse5("parseArgumentList", "()", []);
     NodeList<Expression> arguments8 = argumentList.arguments;
     EngineTestCase.assertSize(0, arguments8);
   }
   void test_parseArgumentList_mixed() {
-    ArgumentList argumentList = ParserTestCase.parse6("parseArgumentList", "(w, x, y: y, z: z)", []);
+    ArgumentList argumentList = ParserTestCase.parse5("parseArgumentList", "(w, x, y: y, z: z)", []);
     NodeList<Expression> arguments9 = argumentList.arguments;
     EngineTestCase.assertSize(4, arguments9);
   }
   void test_parseArgumentList_noNamed() {
-    ArgumentList argumentList = ParserTestCase.parse6("parseArgumentList", "(x, y, z)", []);
+    ArgumentList argumentList = ParserTestCase.parse5("parseArgumentList", "(x, y, z)", []);
     NodeList<Expression> arguments10 = argumentList.arguments;
     EngineTestCase.assertSize(3, arguments10);
   }
   void test_parseArgumentList_onlyNamed() {
-    ArgumentList argumentList = ParserTestCase.parse6("parseArgumentList", "(x: x, y: y)", []);
+    ArgumentList argumentList = ParserTestCase.parse5("parseArgumentList", "(x: x, y: y)", []);
     NodeList<Expression> arguments11 = argumentList.arguments;
     EngineTestCase.assertSize(2, arguments11);
   }
   void test_parseAssertStatement() {
-    AssertStatement statement = ParserTestCase.parse6("parseAssertStatement", "assert (x);", []);
+    AssertStatement statement = ParserTestCase.parse5("parseAssertStatement", "assert (x);", []);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.condition);
@@ -386,111 +386,111 @@
     JUnitTestCase.assertNotNull(selector);
   }
   void test_parseBitwiseAndExpression_normal() {
-    BinaryExpression expression = ParserTestCase.parse6("parseBitwiseAndExpression", "x & y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseBitwiseAndExpression", "x & y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.AMPERSAND, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseBitwiseAndExpression_super() {
-    BinaryExpression expression = ParserTestCase.parse6("parseBitwiseAndExpression", "super & y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseBitwiseAndExpression", "super & y", []);
     EngineTestCase.assertInstanceOf(SuperExpression, expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.AMPERSAND, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseBitwiseOrExpression_normal() {
-    BinaryExpression expression = ParserTestCase.parse6("parseBitwiseOrExpression", "x | y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseBitwiseOrExpression", "x | y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.BAR, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseBitwiseOrExpression_super() {
-    BinaryExpression expression = ParserTestCase.parse6("parseBitwiseOrExpression", "super | y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseBitwiseOrExpression", "super | y", []);
     EngineTestCase.assertInstanceOf(SuperExpression, expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.BAR, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseBitwiseXorExpression_normal() {
-    BinaryExpression expression = ParserTestCase.parse6("parseBitwiseXorExpression", "x ^ y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseBitwiseXorExpression", "x ^ y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.CARET, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseBitwiseXorExpression_super() {
-    BinaryExpression expression = ParserTestCase.parse6("parseBitwiseXorExpression", "super ^ y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseBitwiseXorExpression", "super ^ y", []);
     EngineTestCase.assertInstanceOf(SuperExpression, expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.CARET, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseBlock_empty() {
-    Block block = ParserTestCase.parse6("parseBlock", "{}", []);
+    Block block = ParserTestCase.parse5("parseBlock", "{}", []);
     JUnitTestCase.assertNotNull(block.leftBracket);
     EngineTestCase.assertSize(0, block.statements);
     JUnitTestCase.assertNotNull(block.rightBracket);
   }
   void test_parseBlock_nonEmpty() {
-    Block block = ParserTestCase.parse6("parseBlock", "{;}", []);
+    Block block = ParserTestCase.parse5("parseBlock", "{;}", []);
     JUnitTestCase.assertNotNull(block.leftBracket);
     EngineTestCase.assertSize(1, block.statements);
     JUnitTestCase.assertNotNull(block.rightBracket);
   }
   void test_parseBreakStatement_label() {
-    BreakStatement statement = ParserTestCase.parse6("parseBreakStatement", "break foo;", []);
+    BreakStatement statement = ParserTestCase.parse5("parseBreakStatement", "break foo;", []);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNotNull(statement.label);
     JUnitTestCase.assertNotNull(statement.semicolon);
   }
   void test_parseBreakStatement_noLabel() {
-    BreakStatement statement = ParserTestCase.parse6("parseBreakStatement", "break;", [ParserErrorCode.BREAK_OUTSIDE_OF_LOOP]);
+    BreakStatement statement = ParserTestCase.parse5("parseBreakStatement", "break;", [ParserErrorCode.BREAK_OUTSIDE_OF_LOOP]);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNull(statement.label);
     JUnitTestCase.assertNotNull(statement.semicolon);
   }
   void test_parseCascadeSection_i() {
-    IndexExpression section = ParserTestCase.parse6("parseCascadeSection", "..[i]", []);
+    IndexExpression section = ParserTestCase.parse5("parseCascadeSection", "..[i]", []);
     JUnitTestCase.assertNull(section.array);
     JUnitTestCase.assertNotNull(section.leftBracket);
     JUnitTestCase.assertNotNull(section.index);
     JUnitTestCase.assertNotNull(section.rightBracket);
   }
   void test_parseCascadeSection_ia() {
-    FunctionExpressionInvocation section = ParserTestCase.parse6("parseCascadeSection", "..[i](b)", []);
+    FunctionExpressionInvocation section = ParserTestCase.parse5("parseCascadeSection", "..[i](b)", []);
     EngineTestCase.assertInstanceOf(IndexExpression, section.function);
     JUnitTestCase.assertNotNull(section.argumentList);
   }
   void test_parseCascadeSection_p() {
-    PropertyAccess section = ParserTestCase.parse6("parseCascadeSection", "..a", []);
+    PropertyAccess section = ParserTestCase.parse5("parseCascadeSection", "..a", []);
     JUnitTestCase.assertNull(section.target);
     JUnitTestCase.assertNotNull(section.operator);
     JUnitTestCase.assertNotNull(section.propertyName);
   }
   void test_parseCascadeSection_p_assign() {
-    AssignmentExpression section = ParserTestCase.parse6("parseCascadeSection", "..a = 3", []);
+    AssignmentExpression section = ParserTestCase.parse5("parseCascadeSection", "..a = 3", []);
     JUnitTestCase.assertNotNull(section.leftHandSide);
     JUnitTestCase.assertNotNull(section.operator);
     Expression rhs = section.rightHandSide;
     JUnitTestCase.assertNotNull(rhs);
   }
   void test_parseCascadeSection_p_assign_withCascade() {
-    AssignmentExpression section = ParserTestCase.parse6("parseCascadeSection", "..a = 3..m()", []);
+    AssignmentExpression section = ParserTestCase.parse5("parseCascadeSection", "..a = 3..m()", []);
     JUnitTestCase.assertNotNull(section.leftHandSide);
     JUnitTestCase.assertNotNull(section.operator);
     Expression rhs = section.rightHandSide;
     EngineTestCase.assertInstanceOf(IntegerLiteral, rhs);
   }
   void test_parseCascadeSection_p_builtIn() {
-    PropertyAccess section = ParserTestCase.parse6("parseCascadeSection", "..as", []);
+    PropertyAccess section = ParserTestCase.parse5("parseCascadeSection", "..as", []);
     JUnitTestCase.assertNull(section.target);
     JUnitTestCase.assertNotNull(section.operator);
     JUnitTestCase.assertNotNull(section.propertyName);
   }
   void test_parseCascadeSection_pa() {
-    MethodInvocation section = ParserTestCase.parse6("parseCascadeSection", "..a(b)", []);
+    MethodInvocation section = ParserTestCase.parse5("parseCascadeSection", "..a(b)", []);
     JUnitTestCase.assertNull(section.target);
     JUnitTestCase.assertNotNull(section.period);
     JUnitTestCase.assertNotNull(section.methodName);
@@ -498,19 +498,19 @@
     EngineTestCase.assertSize(1, section.argumentList.arguments);
   }
   void test_parseCascadeSection_paa() {
-    FunctionExpressionInvocation section = ParserTestCase.parse6("parseCascadeSection", "..a(b)(c)", []);
+    FunctionExpressionInvocation section = ParserTestCase.parse5("parseCascadeSection", "..a(b)(c)", []);
     EngineTestCase.assertInstanceOf(MethodInvocation, section.function);
     JUnitTestCase.assertNotNull(section.argumentList);
     EngineTestCase.assertSize(1, section.argumentList.arguments);
   }
   void test_parseCascadeSection_paapaa() {
-    FunctionExpressionInvocation section = ParserTestCase.parse6("parseCascadeSection", "..a(b)(c).d(e)(f)", []);
+    FunctionExpressionInvocation section = ParserTestCase.parse5("parseCascadeSection", "..a(b)(c).d(e)(f)", []);
     EngineTestCase.assertInstanceOf(FunctionExpressionInvocation, section.function);
     JUnitTestCase.assertNotNull(section.argumentList);
     EngineTestCase.assertSize(1, section.argumentList.arguments);
   }
   void test_parseCascadeSection_pap() {
-    PropertyAccess section = ParserTestCase.parse6("parseCascadeSection", "..a(b).c", []);
+    PropertyAccess section = ParserTestCase.parse5("parseCascadeSection", "..a(b).c", []);
     JUnitTestCase.assertNotNull(section.target);
     JUnitTestCase.assertNotNull(section.operator);
     JUnitTestCase.assertNotNull(section.propertyName);
@@ -904,7 +904,7 @@
     JUnitTestCase.assertNotNull(constructor.body);
   }
   void test_parseCombinators_h() {
-    List<Combinator> combinators = ParserTestCase.parse6("parseCombinators", "hide a;", []);
+    List<Combinator> combinators = ParserTestCase.parse5("parseCombinators", "hide a;", []);
     EngineTestCase.assertSize(1, combinators);
     HideCombinator combinator = combinators[0] as HideCombinator;
     JUnitTestCase.assertNotNull(combinator);
@@ -912,7 +912,7 @@
     EngineTestCase.assertSize(1, combinator.hiddenNames);
   }
   void test_parseCombinators_hs() {
-    List<Combinator> combinators = ParserTestCase.parse6("parseCombinators", "hide a show b;", []);
+    List<Combinator> combinators = ParserTestCase.parse5("parseCombinators", "hide a show b;", []);
     EngineTestCase.assertSize(2, combinators);
     HideCombinator hideCombinator = combinators[0] as HideCombinator;
     JUnitTestCase.assertNotNull(hideCombinator);
@@ -924,11 +924,11 @@
     EngineTestCase.assertSize(1, showCombinator.shownNames);
   }
   void test_parseCombinators_hshs() {
-    List<Combinator> combinators = ParserTestCase.parse6("parseCombinators", "hide a show b hide c show d;", []);
+    List<Combinator> combinators = ParserTestCase.parse5("parseCombinators", "hide a show b hide c show d;", []);
     EngineTestCase.assertSize(4, combinators);
   }
   void test_parseCombinators_s() {
-    List<Combinator> combinators = ParserTestCase.parse6("parseCombinators", "show a;", []);
+    List<Combinator> combinators = ParserTestCase.parse5("parseCombinators", "show a;", []);
     EngineTestCase.assertSize(1, combinators);
     ShowCombinator combinator = combinators[0] as ShowCombinator;
     JUnitTestCase.assertNotNull(combinator);
@@ -936,47 +936,47 @@
     EngineTestCase.assertSize(1, combinator.shownNames);
   }
   void test_parseCommentAndMetadata_c() {
-    CommentAndMetadata commentAndMetadata = ParserTestCase.parse6("parseCommentAndMetadata", "/** 1 */ void", []);
+    CommentAndMetadata commentAndMetadata = ParserTestCase.parse5("parseCommentAndMetadata", "/** 1 */ void", []);
     JUnitTestCase.assertNotNull(commentAndMetadata.comment);
     EngineTestCase.assertSize(0, commentAndMetadata.metadata);
   }
   void test_parseCommentAndMetadata_cmc() {
-    CommentAndMetadata commentAndMetadata = ParserTestCase.parse6("parseCommentAndMetadata", "/** 1 */ @A /** 2 */ void", []);
+    CommentAndMetadata commentAndMetadata = ParserTestCase.parse5("parseCommentAndMetadata", "/** 1 */ @A /** 2 */ void", []);
     JUnitTestCase.assertNotNull(commentAndMetadata.comment);
     EngineTestCase.assertSize(1, commentAndMetadata.metadata);
   }
   void test_parseCommentAndMetadata_cmcm() {
-    CommentAndMetadata commentAndMetadata = ParserTestCase.parse6("parseCommentAndMetadata", "/** 1 */ @A /** 2 */ @B void", []);
+    CommentAndMetadata commentAndMetadata = ParserTestCase.parse5("parseCommentAndMetadata", "/** 1 */ @A /** 2 */ @B void", []);
     JUnitTestCase.assertNotNull(commentAndMetadata.comment);
     EngineTestCase.assertSize(2, commentAndMetadata.metadata);
   }
   void test_parseCommentAndMetadata_cmm() {
-    CommentAndMetadata commentAndMetadata = ParserTestCase.parse6("parseCommentAndMetadata", "/** 1 */ @A @B void", []);
+    CommentAndMetadata commentAndMetadata = ParserTestCase.parse5("parseCommentAndMetadata", "/** 1 */ @A @B void", []);
     JUnitTestCase.assertNotNull(commentAndMetadata.comment);
     EngineTestCase.assertSize(2, commentAndMetadata.metadata);
   }
   void test_parseCommentAndMetadata_m() {
-    CommentAndMetadata commentAndMetadata = ParserTestCase.parse6("parseCommentAndMetadata", "@A void", []);
+    CommentAndMetadata commentAndMetadata = ParserTestCase.parse5("parseCommentAndMetadata", "@A void", []);
     JUnitTestCase.assertNull(commentAndMetadata.comment);
     EngineTestCase.assertSize(1, commentAndMetadata.metadata);
   }
   void test_parseCommentAndMetadata_mcm() {
-    CommentAndMetadata commentAndMetadata = ParserTestCase.parse6("parseCommentAndMetadata", "@A /** 1 */ @B void", []);
+    CommentAndMetadata commentAndMetadata = ParserTestCase.parse5("parseCommentAndMetadata", "@A /** 1 */ @B void", []);
     JUnitTestCase.assertNotNull(commentAndMetadata.comment);
     EngineTestCase.assertSize(2, commentAndMetadata.metadata);
   }
   void test_parseCommentAndMetadata_mcmc() {
-    CommentAndMetadata commentAndMetadata = ParserTestCase.parse6("parseCommentAndMetadata", "@A /** 1 */ @B /** 2 */ void", []);
+    CommentAndMetadata commentAndMetadata = ParserTestCase.parse5("parseCommentAndMetadata", "@A /** 1 */ @B /** 2 */ void", []);
     JUnitTestCase.assertNotNull(commentAndMetadata.comment);
     EngineTestCase.assertSize(2, commentAndMetadata.metadata);
   }
   void test_parseCommentAndMetadata_mm() {
-    CommentAndMetadata commentAndMetadata = ParserTestCase.parse6("parseCommentAndMetadata", "@A @B(x) void", []);
+    CommentAndMetadata commentAndMetadata = ParserTestCase.parse5("parseCommentAndMetadata", "@A @B(x) void", []);
     JUnitTestCase.assertNull(commentAndMetadata.comment);
     EngineTestCase.assertSize(2, commentAndMetadata.metadata);
   }
   void test_parseCommentAndMetadata_none() {
-    CommentAndMetadata commentAndMetadata = ParserTestCase.parse6("parseCommentAndMetadata", "void", []);
+    CommentAndMetadata commentAndMetadata = ParserTestCase.parse5("parseCommentAndMetadata", "void", []);
     JUnitTestCase.assertNull(commentAndMetadata.comment);
     EngineTestCase.assertSize(0, commentAndMetadata.metadata);
   }
@@ -1051,61 +1051,61 @@
     JUnitTestCase.assertEquals(35, reference.offset);
   }
   void test_parseCompilationUnit_abstractAsPrefix_parameterized() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "abstract<dynamic> _abstract = new abstract.A();", []);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "abstract<dynamic> _abstract = new abstract.A();", []);
     JUnitTestCase.assertNull(unit.scriptTag);
     EngineTestCase.assertSize(0, unit.directives);
     EngineTestCase.assertSize(1, unit.declarations);
   }
   void test_parseCompilationUnit_directives_multiple() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "library l;\npart 'a.dart';", []);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "library l;\npart 'a.dart';", []);
     JUnitTestCase.assertNull(unit.scriptTag);
     EngineTestCase.assertSize(2, unit.directives);
     EngineTestCase.assertSize(0, unit.declarations);
   }
   void test_parseCompilationUnit_directives_single() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "library l;", []);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "library l;", []);
     JUnitTestCase.assertNull(unit.scriptTag);
     EngineTestCase.assertSize(1, unit.directives);
     EngineTestCase.assertSize(0, unit.declarations);
   }
   void test_parseCompilationUnit_empty() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "", []);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "", []);
     JUnitTestCase.assertNull(unit.scriptTag);
     EngineTestCase.assertSize(0, unit.directives);
     EngineTestCase.assertSize(0, unit.declarations);
   }
   void test_parseCompilationUnit_exportAsPrefix() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "export.A _export = new export.A();", []);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "export.A _export = new export.A();", []);
     JUnitTestCase.assertNull(unit.scriptTag);
     EngineTestCase.assertSize(0, unit.directives);
     EngineTestCase.assertSize(1, unit.declarations);
   }
   void test_parseCompilationUnit_exportAsPrefix_parameterized() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "export<dynamic> _export = new export.A();", []);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "export<dynamic> _export = new export.A();", []);
     JUnitTestCase.assertNull(unit.scriptTag);
     EngineTestCase.assertSize(0, unit.directives);
     EngineTestCase.assertSize(1, unit.declarations);
   }
   void test_parseCompilationUnit_operatorAsPrefix_parameterized() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "operator<dynamic> _operator = new operator.A();", []);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "operator<dynamic> _operator = new operator.A();", []);
     JUnitTestCase.assertNull(unit.scriptTag);
     EngineTestCase.assertSize(0, unit.directives);
     EngineTestCase.assertSize(1, unit.declarations);
   }
   void test_parseCompilationUnit_script() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "#! /bin/dart", []);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "#! /bin/dart", []);
     JUnitTestCase.assertNotNull(unit.scriptTag);
     EngineTestCase.assertSize(0, unit.directives);
     EngineTestCase.assertSize(0, unit.declarations);
   }
   void test_parseCompilationUnit_topLevelDeclaration() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "class A {}", []);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "class A {}", []);
     JUnitTestCase.assertNull(unit.scriptTag);
     EngineTestCase.assertSize(0, unit.directives);
     EngineTestCase.assertSize(1, unit.declarations);
   }
   void test_parseCompilationUnit_typedefAsPrefix() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "typedef.A _typedef = new typedef.A();", []);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "typedef.A _typedef = new typedef.A();", []);
     JUnitTestCase.assertNull(unit.scriptTag);
     EngineTestCase.assertSize(0, unit.directives);
     EngineTestCase.assertSize(1, unit.declarations);
@@ -1255,7 +1255,7 @@
     JUnitTestCase.assertNotNull(declaration.variables);
   }
   void test_parseConditionalExpression() {
-    ConditionalExpression expression = ParserTestCase.parse6("parseConditionalExpression", "x ? y : z", []);
+    ConditionalExpression expression = ParserTestCase.parse5("parseConditionalExpression", "x ? y : z", []);
     JUnitTestCase.assertNotNull(expression.condition);
     JUnitTestCase.assertNotNull(expression.question);
     JUnitTestCase.assertNotNull(expression.thenExpression);
@@ -1263,7 +1263,7 @@
     JUnitTestCase.assertNotNull(expression.elseExpression);
   }
   void test_parseConstExpression_instanceCreation() {
-    InstanceCreationExpression expression = ParserTestCase.parse6("parseConstExpression", "const A()", []);
+    InstanceCreationExpression expression = ParserTestCase.parse5("parseConstExpression", "const A()", []);
     JUnitTestCase.assertNotNull(expression.keyword);
     ConstructorName name = expression.constructorName;
     JUnitTestCase.assertNotNull(name);
@@ -1273,7 +1273,7 @@
     JUnitTestCase.assertNotNull(expression.argumentList);
   }
   void test_parseConstExpression_listLiteral_typed() {
-    ListLiteral literal = ParserTestCase.parse6("parseConstExpression", "const <A> []", []);
+    ListLiteral literal = ParserTestCase.parse5("parseConstExpression", "const <A> []", []);
     JUnitTestCase.assertNotNull(literal.modifier);
     JUnitTestCase.assertNotNull(literal.typeArguments);
     JUnitTestCase.assertNotNull(literal.leftBracket);
@@ -1281,7 +1281,7 @@
     JUnitTestCase.assertNotNull(literal.rightBracket);
   }
   void test_parseConstExpression_listLiteral_untyped() {
-    ListLiteral literal = ParserTestCase.parse6("parseConstExpression", "const []", []);
+    ListLiteral literal = ParserTestCase.parse5("parseConstExpression", "const []", []);
     JUnitTestCase.assertNotNull(literal.modifier);
     JUnitTestCase.assertNull(literal.typeArguments);
     JUnitTestCase.assertNotNull(literal.leftBracket);
@@ -1289,14 +1289,14 @@
     JUnitTestCase.assertNotNull(literal.rightBracket);
   }
   void test_parseConstExpression_mapLiteral_typed() {
-    MapLiteral literal = ParserTestCase.parse6("parseConstExpression", "const <A> {}", []);
+    MapLiteral literal = ParserTestCase.parse5("parseConstExpression", "const <A> {}", []);
     JUnitTestCase.assertNotNull(literal.leftBracket);
     EngineTestCase.assertSize(0, literal.entries);
     JUnitTestCase.assertNotNull(literal.rightBracket);
     JUnitTestCase.assertNotNull(literal.typeArguments);
   }
   void test_parseConstExpression_mapLiteral_untyped() {
-    MapLiteral literal = ParserTestCase.parse6("parseConstExpression", "const {}", []);
+    MapLiteral literal = ParserTestCase.parse5("parseConstExpression", "const {}", []);
     JUnitTestCase.assertNotNull(literal.leftBracket);
     EngineTestCase.assertSize(0, literal.entries);
     JUnitTestCase.assertNotNull(literal.rightBracket);
@@ -1305,7 +1305,7 @@
   void test_parseConstructor() {
   }
   void test_parseConstructorFieldInitializer_qualified() {
-    ConstructorFieldInitializer invocation = ParserTestCase.parse6("parseConstructorFieldInitializer", "this.a = b", []);
+    ConstructorFieldInitializer invocation = ParserTestCase.parse5("parseConstructorFieldInitializer", "this.a = b", []);
     JUnitTestCase.assertNotNull(invocation.equals);
     JUnitTestCase.assertNotNull(invocation.expression);
     JUnitTestCase.assertNotNull(invocation.fieldName);
@@ -1313,7 +1313,7 @@
     JUnitTestCase.assertNotNull(invocation.period);
   }
   void test_parseConstructorFieldInitializer_unqualified() {
-    ConstructorFieldInitializer invocation = ParserTestCase.parse6("parseConstructorFieldInitializer", "a = b", []);
+    ConstructorFieldInitializer invocation = ParserTestCase.parse5("parseConstructorFieldInitializer", "a = b", []);
     JUnitTestCase.assertNotNull(invocation.equals);
     JUnitTestCase.assertNotNull(invocation.expression);
     JUnitTestCase.assertNotNull(invocation.fieldName);
@@ -1321,63 +1321,41 @@
     JUnitTestCase.assertNull(invocation.period);
   }
   void test_parseConstructorName_named_noPrefix() {
-    ConstructorName name = ParserTestCase.parse6("parseConstructorName", "A.n;", []);
+    ConstructorName name = ParserTestCase.parse5("parseConstructorName", "A.n;", []);
     JUnitTestCase.assertNotNull(name.type);
     JUnitTestCase.assertNull(name.period);
     JUnitTestCase.assertNull(name.name);
   }
   void test_parseConstructorName_named_prefixed() {
-    ConstructorName name = ParserTestCase.parse6("parseConstructorName", "p.A.n;", []);
+    ConstructorName name = ParserTestCase.parse5("parseConstructorName", "p.A.n;", []);
     JUnitTestCase.assertNotNull(name.type);
     JUnitTestCase.assertNotNull(name.period);
     JUnitTestCase.assertNotNull(name.name);
   }
   void test_parseConstructorName_unnamed_noPrefix() {
-    ConstructorName name = ParserTestCase.parse6("parseConstructorName", "A;", []);
+    ConstructorName name = ParserTestCase.parse5("parseConstructorName", "A;", []);
     JUnitTestCase.assertNotNull(name.type);
     JUnitTestCase.assertNull(name.period);
     JUnitTestCase.assertNull(name.name);
   }
   void test_parseConstructorName_unnamed_prefixed() {
-    ConstructorName name = ParserTestCase.parse6("parseConstructorName", "p.A;", []);
+    ConstructorName name = ParserTestCase.parse5("parseConstructorName", "p.A;", []);
     JUnitTestCase.assertNotNull(name.type);
     JUnitTestCase.assertNull(name.period);
     JUnitTestCase.assertNull(name.name);
   }
   void test_parseContinueStatement_label() {
-    ContinueStatement statement = ParserTestCase.parse6("parseContinueStatement", "continue foo;", [ParserErrorCode.CONTINUE_OUTSIDE_OF_LOOP]);
+    ContinueStatement statement = ParserTestCase.parse5("parseContinueStatement", "continue foo;", [ParserErrorCode.CONTINUE_OUTSIDE_OF_LOOP]);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNotNull(statement.label);
     JUnitTestCase.assertNotNull(statement.semicolon);
   }
   void test_parseContinueStatement_noLabel() {
-    ContinueStatement statement = ParserTestCase.parse6("parseContinueStatement", "continue;", [ParserErrorCode.CONTINUE_OUTSIDE_OF_LOOP]);
+    ContinueStatement statement = ParserTestCase.parse5("parseContinueStatement", "continue;", [ParserErrorCode.CONTINUE_OUTSIDE_OF_LOOP]);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNull(statement.label);
     JUnitTestCase.assertNotNull(statement.semicolon);
   }
-  void test_parseDeclaredIdentifier_const() {
-    DeclaredIdentifier declaredIdentifier = ParserTestCase.parse("parseDeclaredIdentifier", <Object> [emptyCommentAndMetadata()], "const A a");
-    JUnitTestCase.assertNotNull(declaredIdentifier.keyword);
-    JUnitTestCase.assertTrue(declaredIdentifier.isConst());
-    JUnitTestCase.assertNotNull(declaredIdentifier.type);
-  }
-  void test_parseDeclaredIdentifier_final() {
-    DeclaredIdentifier declaredIdentifier = ParserTestCase.parse("parseDeclaredIdentifier", <Object> [emptyCommentAndMetadata()], "final A a");
-    JUnitTestCase.assertNotNull(declaredIdentifier.keyword);
-    JUnitTestCase.assertTrue(declaredIdentifier.isFinal());
-    JUnitTestCase.assertNotNull(declaredIdentifier.type);
-  }
-  void test_parseDeclaredIdentifier_type() {
-    DeclaredIdentifier declaredIdentifier = ParserTestCase.parse("parseDeclaredIdentifier", <Object> [emptyCommentAndMetadata()], "A a");
-    JUnitTestCase.assertNull(declaredIdentifier.keyword);
-    JUnitTestCase.assertNotNull(declaredIdentifier.type);
-  }
-  void test_parseDeclaredIdentifier_var() {
-    DeclaredIdentifier declaredIdentifier = ParserTestCase.parse("parseDeclaredIdentifier", <Object> [emptyCommentAndMetadata()], "var a");
-    JUnitTestCase.assertNotNull(declaredIdentifier.keyword);
-    JUnitTestCase.assertNull(declaredIdentifier.type);
-  }
   void test_parseDirective_export() {
     ExportDirective directive = ParserTestCase.parse("parseDirective", <Object> [emptyCommentAndMetadata()], "export 'lib/lib.dart';");
     JUnitTestCase.assertNotNull(directive.keyword);
@@ -1414,13 +1392,13 @@
     JUnitTestCase.assertNotNull(directive.semicolon);
   }
   void test_parseDocumentationComment_block() {
-    Comment comment = ParserTestCase.parse6("parseDocumentationComment", "/** */ class", []);
+    Comment comment = ParserTestCase.parse5("parseDocumentationComment", "/** */ class", []);
     JUnitTestCase.assertFalse(comment.isBlock());
     JUnitTestCase.assertTrue(comment.isDocumentation());
     JUnitTestCase.assertFalse(comment.isEndOfLine());
   }
   void test_parseDocumentationComment_block_withReference() {
-    Comment comment = ParserTestCase.parse6("parseDocumentationComment", "/** [a] */ class", []);
+    Comment comment = ParserTestCase.parse5("parseDocumentationComment", "/** [a] */ class", []);
     JUnitTestCase.assertFalse(comment.isBlock());
     JUnitTestCase.assertTrue(comment.isDocumentation());
     JUnitTestCase.assertFalse(comment.isEndOfLine());
@@ -1431,13 +1409,13 @@
     JUnitTestCase.assertEquals(5, reference.offset);
   }
   void test_parseDocumentationComment_endOfLine() {
-    Comment comment = ParserTestCase.parse6("parseDocumentationComment", "/// \n/// \n class", []);
+    Comment comment = ParserTestCase.parse5("parseDocumentationComment", "/// \n/// \n class", []);
     JUnitTestCase.assertFalse(comment.isBlock());
     JUnitTestCase.assertTrue(comment.isDocumentation());
     JUnitTestCase.assertFalse(comment.isEndOfLine());
   }
   void test_parseDoStatement() {
-    DoStatement statement = ParserTestCase.parse6("parseDoStatement", "do {} while (x);", []);
+    DoStatement statement = ParserTestCase.parse5("parseDoStatement", "do {} while (x);", []);
     JUnitTestCase.assertNotNull(statement.doKeyword);
     JUnitTestCase.assertNotNull(statement.body);
     JUnitTestCase.assertNotNull(statement.whileKeyword);
@@ -1447,18 +1425,18 @@
     JUnitTestCase.assertNotNull(statement.semicolon);
   }
   void test_parseEmptyStatement() {
-    EmptyStatement statement = ParserTestCase.parse6("parseEmptyStatement", ";", []);
+    EmptyStatement statement = ParserTestCase.parse5("parseEmptyStatement", ";", []);
     JUnitTestCase.assertNotNull(statement.semicolon);
   }
   void test_parseEqualityExpression_normal() {
-    BinaryExpression expression = ParserTestCase.parse6("parseEqualityExpression", "x == y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseEqualityExpression", "x == y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.EQ_EQ, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseEqualityExpression_super() {
-    BinaryExpression expression = ParserTestCase.parse6("parseEqualityExpression", "super == y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseEqualityExpression", "super == y", []);
     EngineTestCase.assertInstanceOf(SuperExpression, expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.EQ_EQ, expression.operator.type);
@@ -1500,21 +1478,21 @@
     JUnitTestCase.assertNotNull(directive.semicolon);
   }
   void test_parseExpression_assign() {
-    AssignmentExpression expression = ParserTestCase.parse6("parseExpression", "x = y", []);
+    AssignmentExpression expression = ParserTestCase.parse5("parseExpression", "x = y", []);
     JUnitTestCase.assertNotNull(expression.leftHandSide);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.EQ, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightHandSide);
   }
   void test_parseExpression_comparison() {
-    BinaryExpression expression = ParserTestCase.parse6("parseExpression", "--a.b == c", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseExpression", "--a.b == c", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.EQ_EQ, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseExpression_invokeFunctionExpression() {
-    FunctionExpressionInvocation invocation = ParserTestCase.parse6("parseExpression", "(a) {return a + a;} (3)", []);
+    FunctionExpressionInvocation invocation = ParserTestCase.parse5("parseExpression", "(a) {return a + a;} (3)", []);
     EngineTestCase.assertInstanceOf(FunctionExpression, invocation.function);
     FunctionExpression expression = invocation.function as FunctionExpression;
     JUnitTestCase.assertNotNull(expression.parameters);
@@ -1524,75 +1502,75 @@
     EngineTestCase.assertSize(1, list.arguments);
   }
   void test_parseExpression_superMethodInvocation() {
-    MethodInvocation invocation = ParserTestCase.parse6("parseExpression", "super.m()", []);
+    MethodInvocation invocation = ParserTestCase.parse5("parseExpression", "super.m()", []);
     JUnitTestCase.assertNotNull(invocation.target);
     JUnitTestCase.assertNotNull(invocation.methodName);
     JUnitTestCase.assertNotNull(invocation.argumentList);
   }
   void test_parseExpressionList_multiple() {
-    List<Expression> result = ParserTestCase.parse6("parseExpressionList", "1, 2, 3", []);
+    List<Expression> result = ParserTestCase.parse5("parseExpressionList", "1, 2, 3", []);
     EngineTestCase.assertSize(3, result);
   }
   void test_parseExpressionList_single() {
-    List<Expression> result = ParserTestCase.parse6("parseExpressionList", "1", []);
+    List<Expression> result = ParserTestCase.parse5("parseExpressionList", "1", []);
     EngineTestCase.assertSize(1, result);
   }
   void test_parseExpressionWithoutCascade_assign() {
-    AssignmentExpression expression = ParserTestCase.parse6("parseExpressionWithoutCascade", "x = y", []);
+    AssignmentExpression expression = ParserTestCase.parse5("parseExpressionWithoutCascade", "x = y", []);
     JUnitTestCase.assertNotNull(expression.leftHandSide);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.EQ, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightHandSide);
   }
   void test_parseExpressionWithoutCascade_comparison() {
-    BinaryExpression expression = ParserTestCase.parse6("parseExpressionWithoutCascade", "--a.b == c", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseExpressionWithoutCascade", "--a.b == c", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.EQ_EQ, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseExpressionWithoutCascade_superMethodInvocation() {
-    MethodInvocation invocation = ParserTestCase.parse6("parseExpressionWithoutCascade", "super.m()", []);
+    MethodInvocation invocation = ParserTestCase.parse5("parseExpressionWithoutCascade", "super.m()", []);
     JUnitTestCase.assertNotNull(invocation.target);
     JUnitTestCase.assertNotNull(invocation.methodName);
     JUnitTestCase.assertNotNull(invocation.argumentList);
   }
   void test_parseExtendsClause() {
-    ExtendsClause clause = ParserTestCase.parse6("parseExtendsClause", "extends B", []);
+    ExtendsClause clause = ParserTestCase.parse5("parseExtendsClause", "extends B", []);
     JUnitTestCase.assertNotNull(clause.keyword);
     JUnitTestCase.assertNotNull(clause.superclass);
     EngineTestCase.assertInstanceOf(TypeName, clause.superclass);
   }
   void test_parseFinalConstVarOrType_const_noType() {
     FinalConstVarOrType result = ParserTestCase.parse("parseFinalConstVarOrType", <Object> [false], "const");
-    Token keyword31 = result.keyword;
-    JUnitTestCase.assertNotNull(keyword31);
-    JUnitTestCase.assertEquals(TokenType.KEYWORD, keyword31.type);
-    JUnitTestCase.assertEquals(Keyword.CONST, ((keyword31 as KeywordToken)).keyword);
-    JUnitTestCase.assertNull(result.type);
-  }
-  void test_parseFinalConstVarOrType_const_type() {
-    FinalConstVarOrType result = ParserTestCase.parse("parseFinalConstVarOrType", <Object> [false], "const A a");
     Token keyword32 = result.keyword;
     JUnitTestCase.assertNotNull(keyword32);
     JUnitTestCase.assertEquals(TokenType.KEYWORD, keyword32.type);
     JUnitTestCase.assertEquals(Keyword.CONST, ((keyword32 as KeywordToken)).keyword);
+    JUnitTestCase.assertNull(result.type);
+  }
+  void test_parseFinalConstVarOrType_const_type() {
+    FinalConstVarOrType result = ParserTestCase.parse("parseFinalConstVarOrType", <Object> [false], "const A a");
+    Token keyword33 = result.keyword;
+    JUnitTestCase.assertNotNull(keyword33);
+    JUnitTestCase.assertEquals(TokenType.KEYWORD, keyword33.type);
+    JUnitTestCase.assertEquals(Keyword.CONST, ((keyword33 as KeywordToken)).keyword);
     JUnitTestCase.assertNotNull(result.type);
   }
   void test_parseFinalConstVarOrType_final_noType() {
     FinalConstVarOrType result = ParserTestCase.parse("parseFinalConstVarOrType", <Object> [false], "final");
-    Token keyword33 = result.keyword;
-    JUnitTestCase.assertNotNull(keyword33);
-    JUnitTestCase.assertEquals(TokenType.KEYWORD, keyword33.type);
-    JUnitTestCase.assertEquals(Keyword.FINAL, ((keyword33 as KeywordToken)).keyword);
-    JUnitTestCase.assertNull(result.type);
-  }
-  void test_parseFinalConstVarOrType_final_type() {
-    FinalConstVarOrType result = ParserTestCase.parse("parseFinalConstVarOrType", <Object> [false], "final A a");
     Token keyword34 = result.keyword;
     JUnitTestCase.assertNotNull(keyword34);
     JUnitTestCase.assertEquals(TokenType.KEYWORD, keyword34.type);
     JUnitTestCase.assertEquals(Keyword.FINAL, ((keyword34 as KeywordToken)).keyword);
+    JUnitTestCase.assertNull(result.type);
+  }
+  void test_parseFinalConstVarOrType_final_type() {
+    FinalConstVarOrType result = ParserTestCase.parse("parseFinalConstVarOrType", <Object> [false], "final A a");
+    Token keyword35 = result.keyword;
+    JUnitTestCase.assertNotNull(keyword35);
+    JUnitTestCase.assertEquals(TokenType.KEYWORD, keyword35.type);
+    JUnitTestCase.assertEquals(Keyword.FINAL, ((keyword35 as KeywordToken)).keyword);
     JUnitTestCase.assertNotNull(result.type);
   }
   void test_parseFinalConstVarOrType_type_parameterized() {
@@ -1617,10 +1595,10 @@
   }
   void test_parseFinalConstVarOrType_var() {
     FinalConstVarOrType result = ParserTestCase.parse("parseFinalConstVarOrType", <Object> [false], "var");
-    Token keyword35 = result.keyword;
-    JUnitTestCase.assertNotNull(keyword35);
-    JUnitTestCase.assertEquals(TokenType.KEYWORD, keyword35.type);
-    JUnitTestCase.assertEquals(Keyword.VAR, ((keyword35 as KeywordToken)).keyword);
+    Token keyword36 = result.keyword;
+    JUnitTestCase.assertNotNull(keyword36);
+    JUnitTestCase.assertEquals(TokenType.KEYWORD, keyword36.type);
+    JUnitTestCase.assertEquals(Keyword.VAR, ((keyword36 as KeywordToken)).keyword);
     JUnitTestCase.assertNull(result.type);
   }
   void test_parseFormalParameter_final_withType_named() {
@@ -1720,7 +1698,7 @@
     JUnitTestCase.assertEquals(kind, parameter.kind);
   }
   void test_parseFormalParameterList_empty() {
-    FormalParameterList parameterList = ParserTestCase.parse6("parseFormalParameterList", "()", []);
+    FormalParameterList parameterList = ParserTestCase.parse5("parseFormalParameterList", "()", []);
     JUnitTestCase.assertNotNull(parameterList.leftParenthesis);
     JUnitTestCase.assertNull(parameterList.leftDelimiter);
     EngineTestCase.assertSize(0, parameterList.parameters);
@@ -1728,7 +1706,7 @@
     JUnitTestCase.assertNotNull(parameterList.rightParenthesis);
   }
   void test_parseFormalParameterList_named_multiple() {
-    FormalParameterList parameterList = ParserTestCase.parse6("parseFormalParameterList", "({A a : 1, B b, C c : 3})", []);
+    FormalParameterList parameterList = ParserTestCase.parse5("parseFormalParameterList", "({A a : 1, B b, C c : 3})", []);
     JUnitTestCase.assertNotNull(parameterList.leftParenthesis);
     JUnitTestCase.assertNotNull(parameterList.leftDelimiter);
     EngineTestCase.assertSize(3, parameterList.parameters);
@@ -1736,7 +1714,7 @@
     JUnitTestCase.assertNotNull(parameterList.rightParenthesis);
   }
   void test_parseFormalParameterList_named_single() {
-    FormalParameterList parameterList = ParserTestCase.parse6("parseFormalParameterList", "({A a})", []);
+    FormalParameterList parameterList = ParserTestCase.parse5("parseFormalParameterList", "({A a})", []);
     JUnitTestCase.assertNotNull(parameterList.leftParenthesis);
     JUnitTestCase.assertNotNull(parameterList.leftDelimiter);
     EngineTestCase.assertSize(1, parameterList.parameters);
@@ -1744,7 +1722,7 @@
     JUnitTestCase.assertNotNull(parameterList.rightParenthesis);
   }
   void test_parseFormalParameterList_normal_multiple() {
-    FormalParameterList parameterList = ParserTestCase.parse6("parseFormalParameterList", "(A a, B b, C c)", []);
+    FormalParameterList parameterList = ParserTestCase.parse5("parseFormalParameterList", "(A a, B b, C c)", []);
     JUnitTestCase.assertNotNull(parameterList.leftParenthesis);
     JUnitTestCase.assertNull(parameterList.leftDelimiter);
     EngineTestCase.assertSize(3, parameterList.parameters);
@@ -1752,7 +1730,7 @@
     JUnitTestCase.assertNotNull(parameterList.rightParenthesis);
   }
   void test_parseFormalParameterList_normal_named() {
-    FormalParameterList parameterList = ParserTestCase.parse6("parseFormalParameterList", "(A a, {B b})", []);
+    FormalParameterList parameterList = ParserTestCase.parse5("parseFormalParameterList", "(A a, {B b})", []);
     JUnitTestCase.assertNotNull(parameterList.leftParenthesis);
     JUnitTestCase.assertNotNull(parameterList.leftDelimiter);
     EngineTestCase.assertSize(2, parameterList.parameters);
@@ -1760,7 +1738,7 @@
     JUnitTestCase.assertNotNull(parameterList.rightParenthesis);
   }
   void test_parseFormalParameterList_normal_positional() {
-    FormalParameterList parameterList = ParserTestCase.parse6("parseFormalParameterList", "(A a, [B b])", []);
+    FormalParameterList parameterList = ParserTestCase.parse5("parseFormalParameterList", "(A a, [B b])", []);
     JUnitTestCase.assertNotNull(parameterList.leftParenthesis);
     JUnitTestCase.assertNotNull(parameterList.leftDelimiter);
     EngineTestCase.assertSize(2, parameterList.parameters);
@@ -1768,7 +1746,7 @@
     JUnitTestCase.assertNotNull(parameterList.rightParenthesis);
   }
   void test_parseFormalParameterList_normal_single() {
-    FormalParameterList parameterList = ParserTestCase.parse6("parseFormalParameterList", "(A a)", []);
+    FormalParameterList parameterList = ParserTestCase.parse5("parseFormalParameterList", "(A a)", []);
     JUnitTestCase.assertNotNull(parameterList.leftParenthesis);
     JUnitTestCase.assertNull(parameterList.leftDelimiter);
     EngineTestCase.assertSize(1, parameterList.parameters);
@@ -1776,7 +1754,7 @@
     JUnitTestCase.assertNotNull(parameterList.rightParenthesis);
   }
   void test_parseFormalParameterList_positional_multiple() {
-    FormalParameterList parameterList = ParserTestCase.parse6("parseFormalParameterList", "([A a = null, B b, C c = null])", []);
+    FormalParameterList parameterList = ParserTestCase.parse5("parseFormalParameterList", "([A a = null, B b, C c = null])", []);
     JUnitTestCase.assertNotNull(parameterList.leftParenthesis);
     JUnitTestCase.assertNotNull(parameterList.leftDelimiter);
     EngineTestCase.assertSize(3, parameterList.parameters);
@@ -1784,7 +1762,7 @@
     JUnitTestCase.assertNotNull(parameterList.rightParenthesis);
   }
   void test_parseFormalParameterList_positional_single() {
-    FormalParameterList parameterList = ParserTestCase.parse6("parseFormalParameterList", "([A a = null])", []);
+    FormalParameterList parameterList = ParserTestCase.parse5("parseFormalParameterList", "([A a = null])", []);
     JUnitTestCase.assertNotNull(parameterList.leftParenthesis);
     JUnitTestCase.assertNotNull(parameterList.leftDelimiter);
     EngineTestCase.assertSize(1, parameterList.parameters);
@@ -1792,7 +1770,7 @@
     JUnitTestCase.assertNotNull(parameterList.rightParenthesis);
   }
   void test_parseForStatement_each_identifier() {
-    ForEachStatement statement = ParserTestCase.parse6("parseForStatement", "for (element in list) {}", []);
+    ForEachStatement statement = ParserTestCase.parse5("parseForStatement", "for (element in list) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.loopVariable);
@@ -1802,7 +1780,7 @@
     JUnitTestCase.assertNotNull(statement.body);
   }
   void test_parseForStatement_each_noType_metadata() {
-    ForEachStatement statement = ParserTestCase.parse6("parseForStatement", "for (@A var element in list) {}", []);
+    ForEachStatement statement = ParserTestCase.parse5("parseForStatement", "for (@A var element in list) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.loopVariable);
@@ -1813,7 +1791,7 @@
     JUnitTestCase.assertNotNull(statement.body);
   }
   void test_parseForStatement_each_type() {
-    ForEachStatement statement = ParserTestCase.parse6("parseForStatement", "for (A element in list) {}", []);
+    ForEachStatement statement = ParserTestCase.parse5("parseForStatement", "for (A element in list) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.loopVariable);
@@ -1823,7 +1801,7 @@
     JUnitTestCase.assertNotNull(statement.body);
   }
   void test_parseForStatement_each_var() {
-    ForEachStatement statement = ParserTestCase.parse6("parseForStatement", "for (var element in list) {}", []);
+    ForEachStatement statement = ParserTestCase.parse5("parseForStatement", "for (var element in list) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.loopVariable);
@@ -1833,7 +1811,7 @@
     JUnitTestCase.assertNotNull(statement.body);
   }
   void test_parseForStatement_loop_c() {
-    ForStatement statement = ParserTestCase.parse6("parseForStatement", "for (; i < count;) {}", []);
+    ForStatement statement = ParserTestCase.parse5("parseForStatement", "for (; i < count;) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNull(statement.variables);
@@ -1846,7 +1824,7 @@
     JUnitTestCase.assertNotNull(statement.body);
   }
   void test_parseForStatement_loop_cu() {
-    ForStatement statement = ParserTestCase.parse6("parseForStatement", "for (; i < count; i++) {}", []);
+    ForStatement statement = ParserTestCase.parse5("parseForStatement", "for (; i < count; i++) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNull(statement.variables);
@@ -1859,7 +1837,7 @@
     JUnitTestCase.assertNotNull(statement.body);
   }
   void test_parseForStatement_loop_ecu() {
-    ForStatement statement = ParserTestCase.parse6("parseForStatement", "for (i--; i < count; i++) {}", []);
+    ForStatement statement = ParserTestCase.parse5("parseForStatement", "for (i--; i < count; i++) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNull(statement.variables);
@@ -1872,11 +1850,12 @@
     JUnitTestCase.assertNotNull(statement.body);
   }
   void test_parseForStatement_loop_i() {
-    ForStatement statement = ParserTestCase.parse6("parseForStatement", "for (var i = 0;;) {}", []);
+    ForStatement statement = ParserTestCase.parse5("parseForStatement", "for (var i = 0;;) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     VariableDeclarationList variables8 = statement.variables;
     JUnitTestCase.assertNotNull(variables8);
+    EngineTestCase.assertSize(0, variables8.metadata);
     EngineTestCase.assertSize(1, variables8.variables);
     JUnitTestCase.assertNull(statement.initialization);
     JUnitTestCase.assertNotNull(statement.leftSeparator);
@@ -1886,23 +1865,24 @@
     JUnitTestCase.assertNotNull(statement.rightParenthesis);
     JUnitTestCase.assertNotNull(statement.body);
   }
-  void test_parseForStatement_loop_ic() {
-    ForStatement statement = ParserTestCase.parse6("parseForStatement", "for (var i = 0; i < count;) {}", []);
+  void test_parseForStatement_loop_i_withMetadata() {
+    ForStatement statement = ParserTestCase.parse5("parseForStatement", "for (@A var i = 0;;) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     VariableDeclarationList variables9 = statement.variables;
     JUnitTestCase.assertNotNull(variables9);
+    EngineTestCase.assertSize(1, variables9.metadata);
     EngineTestCase.assertSize(1, variables9.variables);
     JUnitTestCase.assertNull(statement.initialization);
     JUnitTestCase.assertNotNull(statement.leftSeparator);
-    JUnitTestCase.assertNotNull(statement.condition);
+    JUnitTestCase.assertNull(statement.condition);
     JUnitTestCase.assertNotNull(statement.rightSeparator);
     EngineTestCase.assertSize(0, statement.updaters);
     JUnitTestCase.assertNotNull(statement.rightParenthesis);
     JUnitTestCase.assertNotNull(statement.body);
   }
-  void test_parseForStatement_loop_icu() {
-    ForStatement statement = ParserTestCase.parse6("parseForStatement", "for (var i = 0; i < count; i++) {}", []);
+  void test_parseForStatement_loop_ic() {
+    ForStatement statement = ParserTestCase.parse5("parseForStatement", "for (var i = 0; i < count;) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     VariableDeclarationList variables10 = statement.variables;
@@ -1912,17 +1892,32 @@
     JUnitTestCase.assertNotNull(statement.leftSeparator);
     JUnitTestCase.assertNotNull(statement.condition);
     JUnitTestCase.assertNotNull(statement.rightSeparator);
+    EngineTestCase.assertSize(0, statement.updaters);
+    JUnitTestCase.assertNotNull(statement.rightParenthesis);
+    JUnitTestCase.assertNotNull(statement.body);
+  }
+  void test_parseForStatement_loop_icu() {
+    ForStatement statement = ParserTestCase.parse5("parseForStatement", "for (var i = 0; i < count; i++) {}", []);
+    JUnitTestCase.assertNotNull(statement.forKeyword);
+    JUnitTestCase.assertNotNull(statement.leftParenthesis);
+    VariableDeclarationList variables11 = statement.variables;
+    JUnitTestCase.assertNotNull(variables11);
+    EngineTestCase.assertSize(1, variables11.variables);
+    JUnitTestCase.assertNull(statement.initialization);
+    JUnitTestCase.assertNotNull(statement.leftSeparator);
+    JUnitTestCase.assertNotNull(statement.condition);
+    JUnitTestCase.assertNotNull(statement.rightSeparator);
     EngineTestCase.assertSize(1, statement.updaters);
     JUnitTestCase.assertNotNull(statement.rightParenthesis);
     JUnitTestCase.assertNotNull(statement.body);
   }
   void test_parseForStatement_loop_iicuu() {
-    ForStatement statement = ParserTestCase.parse6("parseForStatement", "for (int i = 0, j = count; i < j; i++, j--) {}", []);
+    ForStatement statement = ParserTestCase.parse5("parseForStatement", "for (int i = 0, j = count; i < j; i++, j--) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
-    VariableDeclarationList variables11 = statement.variables;
-    JUnitTestCase.assertNotNull(variables11);
-    EngineTestCase.assertSize(2, variables11.variables);
+    VariableDeclarationList variables12 = statement.variables;
+    JUnitTestCase.assertNotNull(variables12);
+    EngineTestCase.assertSize(2, variables12.variables);
     JUnitTestCase.assertNull(statement.initialization);
     JUnitTestCase.assertNotNull(statement.leftSeparator);
     JUnitTestCase.assertNotNull(statement.condition);
@@ -1932,12 +1927,12 @@
     JUnitTestCase.assertNotNull(statement.body);
   }
   void test_parseForStatement_loop_iu() {
-    ForStatement statement = ParserTestCase.parse6("parseForStatement", "for (var i = 0;; i++) {}", []);
+    ForStatement statement = ParserTestCase.parse5("parseForStatement", "for (var i = 0;; i++) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
-    VariableDeclarationList variables12 = statement.variables;
-    JUnitTestCase.assertNotNull(variables12);
-    EngineTestCase.assertSize(1, variables12.variables);
+    VariableDeclarationList variables13 = statement.variables;
+    JUnitTestCase.assertNotNull(variables13);
+    EngineTestCase.assertSize(1, variables13.variables);
     JUnitTestCase.assertNull(statement.initialization);
     JUnitTestCase.assertNotNull(statement.leftSeparator);
     JUnitTestCase.assertNull(statement.condition);
@@ -1947,7 +1942,7 @@
     JUnitTestCase.assertNotNull(statement.body);
   }
   void test_parseForStatement_loop_u() {
-    ForStatement statement = ParserTestCase.parse6("parseForStatement", "for (;; i++) {}", []);
+    ForStatement statement = ParserTestCase.parse5("parseForStatement", "for (;; i++) {}", []);
     JUnitTestCase.assertNotNull(statement.forKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNull(statement.variables);
@@ -2013,17 +2008,17 @@
     JUnitTestCase.assertNotNull(declaration.propertyKeyword);
   }
   void test_parseFunctionDeclarationStatement() {
-    FunctionDeclarationStatement statement = ParserTestCase.parse6("parseFunctionDeclarationStatement", "void f(int p) => p * 2;", []);
+    FunctionDeclarationStatement statement = ParserTestCase.parse5("parseFunctionDeclarationStatement", "void f(int p) => p * 2;", []);
     JUnitTestCase.assertNotNull(statement.functionDeclaration);
   }
   void test_parseFunctionExpression_body_inExpression() {
-    FunctionExpression expression = ParserTestCase.parse6("parseFunctionExpression", "(int i) => i++", []);
+    FunctionExpression expression = ParserTestCase.parse5("parseFunctionExpression", "(int i) => i++", []);
     JUnitTestCase.assertNotNull(expression.body);
     JUnitTestCase.assertNotNull(expression.parameters);
     JUnitTestCase.assertNull(((expression.body as ExpressionFunctionBody)).semicolon);
   }
   void test_parseFunctionExpression_minimal() {
-    FunctionExpression expression = ParserTestCase.parse6("parseFunctionExpression", "() {}", []);
+    FunctionExpression expression = ParserTestCase.parse5("parseFunctionExpression", "() {}", []);
     JUnitTestCase.assertNotNull(expression.body);
     JUnitTestCase.assertNotNull(expression.parameters);
   }
@@ -2057,15 +2052,15 @@
     JUnitTestCase.assertEquals(returnType, method.returnType);
   }
   void test_parseIdentifierList_multiple() {
-    List<SimpleIdentifier> list = ParserTestCase.parse6("parseIdentifierList", "a, b, c", []);
+    List<SimpleIdentifier> list = ParserTestCase.parse5("parseIdentifierList", "a, b, c", []);
     EngineTestCase.assertSize(3, list);
   }
   void test_parseIdentifierList_single() {
-    List<SimpleIdentifier> list = ParserTestCase.parse6("parseIdentifierList", "a", []);
+    List<SimpleIdentifier> list = ParserTestCase.parse5("parseIdentifierList", "a", []);
     EngineTestCase.assertSize(1, list);
   }
   void test_parseIfStatement_else_block() {
-    IfStatement statement = ParserTestCase.parse6("parseIfStatement", "if (x) {} else {}", []);
+    IfStatement statement = ParserTestCase.parse5("parseIfStatement", "if (x) {} else {}", []);
     JUnitTestCase.assertNotNull(statement.ifKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.condition);
@@ -2075,7 +2070,7 @@
     JUnitTestCase.assertNotNull(statement.elseStatement);
   }
   void test_parseIfStatement_else_statement() {
-    IfStatement statement = ParserTestCase.parse6("parseIfStatement", "if (x) f(x); else f(y);", []);
+    IfStatement statement = ParserTestCase.parse5("parseIfStatement", "if (x) f(x); else f(y);", []);
     JUnitTestCase.assertNotNull(statement.ifKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.condition);
@@ -2085,7 +2080,7 @@
     JUnitTestCase.assertNotNull(statement.elseStatement);
   }
   void test_parseIfStatement_noElse_block() {
-    IfStatement statement = ParserTestCase.parse6("parseIfStatement", "if (x) {}", []);
+    IfStatement statement = ParserTestCase.parse5("parseIfStatement", "if (x) {}", []);
     JUnitTestCase.assertNotNull(statement.ifKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.condition);
@@ -2095,7 +2090,7 @@
     JUnitTestCase.assertNull(statement.elseStatement);
   }
   void test_parseIfStatement_noElse_statement() {
-    IfStatement statement = ParserTestCase.parse6("parseIfStatement", "if (x) f(x);", []);
+    IfStatement statement = ParserTestCase.parse5("parseIfStatement", "if (x) f(x);", []);
     JUnitTestCase.assertNotNull(statement.ifKeyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.condition);
@@ -2105,12 +2100,12 @@
     JUnitTestCase.assertNull(statement.elseStatement);
   }
   void test_parseImplementsClause_multiple() {
-    ImplementsClause clause = ParserTestCase.parse6("parseImplementsClause", "implements A, B, C", []);
+    ImplementsClause clause = ParserTestCase.parse5("parseImplementsClause", "implements A, B, C", []);
     EngineTestCase.assertSize(3, clause.interfaces);
     JUnitTestCase.assertNotNull(clause.keyword);
   }
   void test_parseImplementsClause_single() {
-    ImplementsClause clause = ParserTestCase.parse6("parseImplementsClause", "implements A", []);
+    ImplementsClause clause = ParserTestCase.parse5("parseImplementsClause", "implements A", []);
     EngineTestCase.assertSize(1, clause.interfaces);
     JUnitTestCase.assertNotNull(clause.keyword);
   }
@@ -2248,12 +2243,12 @@
   }
   void test_parseLibraryIdentifier_multiple() {
     String name = "a.b.c";
-    LibraryIdentifier identifier = ParserTestCase.parse6("parseLibraryIdentifier", name, []);
+    LibraryIdentifier identifier = ParserTestCase.parse5("parseLibraryIdentifier", name, []);
     JUnitTestCase.assertEquals(name, identifier.name);
   }
   void test_parseLibraryIdentifier_single() {
     String name = "a";
-    LibraryIdentifier identifier = ParserTestCase.parse6("parseLibraryIdentifier", name, []);
+    LibraryIdentifier identifier = ParserTestCase.parse5("parseLibraryIdentifier", name, []);
     JUnitTestCase.assertEquals(name, identifier.name);
   }
   void test_parseListLiteral_empty_oneToken() {
@@ -2325,14 +2320,14 @@
     JUnitTestCase.assertNotNull(literal.rightBracket);
   }
   void test_parseLogicalAndExpression() {
-    BinaryExpression expression = ParserTestCase.parse6("parseLogicalAndExpression", "x && y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseLogicalAndExpression", "x && y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.AMPERSAND_AMPERSAND, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseLogicalOrExpression() {
-    BinaryExpression expression = ParserTestCase.parse6("parseLogicalOrExpression", "x || y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseLogicalOrExpression", "x || y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.BAR_BAR, expression.operator.type);
@@ -2361,55 +2356,55 @@
     JUnitTestCase.assertNotNull(literal.rightBracket);
   }
   void test_parseMapLiteralEntry() {
-    MapLiteralEntry entry = ParserTestCase.parse6("parseMapLiteralEntry", "'x' : y", []);
+    MapLiteralEntry entry = ParserTestCase.parse5("parseMapLiteralEntry", "'x' : y", []);
     JUnitTestCase.assertNotNull(entry.key);
     JUnitTestCase.assertNotNull(entry.separator);
     JUnitTestCase.assertNotNull(entry.value);
   }
   void test_parseModifiers_abstract() {
-    Modifiers modifiers = ParserTestCase.parse6("parseModifiers", "abstract A", []);
+    Modifiers modifiers = ParserTestCase.parse5("parseModifiers", "abstract A", []);
     JUnitTestCase.assertNotNull(modifiers.abstractKeyword);
   }
   void test_parseModifiers_const() {
-    Modifiers modifiers = ParserTestCase.parse6("parseModifiers", "const A", []);
+    Modifiers modifiers = ParserTestCase.parse5("parseModifiers", "const A", []);
     JUnitTestCase.assertNotNull(modifiers.constKeyword);
   }
   void test_parseModifiers_external() {
-    Modifiers modifiers = ParserTestCase.parse6("parseModifiers", "external A", []);
+    Modifiers modifiers = ParserTestCase.parse5("parseModifiers", "external A", []);
     JUnitTestCase.assertNotNull(modifiers.externalKeyword);
   }
   void test_parseModifiers_factory() {
-    Modifiers modifiers = ParserTestCase.parse6("parseModifiers", "factory A", []);
+    Modifiers modifiers = ParserTestCase.parse5("parseModifiers", "factory A", []);
     JUnitTestCase.assertNotNull(modifiers.factoryKeyword);
   }
   void test_parseModifiers_final() {
-    Modifiers modifiers = ParserTestCase.parse6("parseModifiers", "final A", []);
+    Modifiers modifiers = ParserTestCase.parse5("parseModifiers", "final A", []);
     JUnitTestCase.assertNotNull(modifiers.finalKeyword);
   }
   void test_parseModifiers_static() {
-    Modifiers modifiers = ParserTestCase.parse6("parseModifiers", "static A", []);
+    Modifiers modifiers = ParserTestCase.parse5("parseModifiers", "static A", []);
     JUnitTestCase.assertNotNull(modifiers.staticKeyword);
   }
   void test_parseModifiers_var() {
-    Modifiers modifiers = ParserTestCase.parse6("parseModifiers", "var A", []);
+    Modifiers modifiers = ParserTestCase.parse5("parseModifiers", "var A", []);
     JUnitTestCase.assertNotNull(modifiers.varKeyword);
   }
   void test_parseMultiplicativeExpression_normal() {
-    BinaryExpression expression = ParserTestCase.parse6("parseMultiplicativeExpression", "x * y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseMultiplicativeExpression", "x * y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.STAR, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseMultiplicativeExpression_super() {
-    BinaryExpression expression = ParserTestCase.parse6("parseMultiplicativeExpression", "super * y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseMultiplicativeExpression", "super * y", []);
     EngineTestCase.assertInstanceOf(SuperExpression, expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.STAR, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseNewExpression() {
-    InstanceCreationExpression expression = ParserTestCase.parse6("parseNewExpression", "new A()", []);
+    InstanceCreationExpression expression = ParserTestCase.parse5("parseNewExpression", "new A()", []);
     JUnitTestCase.assertNotNull(expression.keyword);
     ConstructorName name = expression.constructorName;
     JUnitTestCase.assertNotNull(name);
@@ -2419,52 +2414,52 @@
     JUnitTestCase.assertNotNull(expression.argumentList);
   }
   void test_parseNonLabeledStatement_const_list_empty() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "const [];", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "const [];", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_const_list_nonEmpty() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "const [1, 2];", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "const [1, 2];", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_const_map_empty() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "const {};", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "const {};", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_const_map_nonEmpty() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "const {'a' : 1};", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "const {'a' : 1};", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_const_object() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "const A();", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "const A();", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_const_object_named_typeParameters() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "const A<B>.c();", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "const A<B>.c();", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_constructorInvocation() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "new C().m();", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "new C().m();", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_false() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "false;", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "false;", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_functionDeclaration() {
-    ParserTestCase.parse6("parseNonLabeledStatement", "f() {};", []);
+    ParserTestCase.parse5("parseNonLabeledStatement", "f() {};", []);
   }
   void test_parseNonLabeledStatement_functionDeclaration_arguments() {
-    ParserTestCase.parse6("parseNonLabeledStatement", "f(void g()) {};", []);
+    ParserTestCase.parse5("parseNonLabeledStatement", "f(void g()) {};", []);
   }
   void test_parseNonLabeledStatement_functionExpressionIndex() {
-    ParserTestCase.parse6("parseNonLabeledStatement", "() {}[0] = null;", []);
+    ParserTestCase.parse5("parseNonLabeledStatement", "() {}[0] = null;", []);
   }
   void test_parseNonLabeledStatement_functionInvocation() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "f();", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "f();", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_invokeFunctionExpression() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "(a) {return a + a;} (3);", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "(a) {return a + a;} (3);", []);
     EngineTestCase.assertInstanceOf(FunctionExpressionInvocation, statement.expression);
     FunctionExpressionInvocation invocation = statement.expression as FunctionExpressionInvocation;
     EngineTestCase.assertInstanceOf(FunctionExpression, invocation.function);
@@ -2476,113 +2471,113 @@
     EngineTestCase.assertSize(1, list.arguments);
   }
   void test_parseNonLabeledStatement_null() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "null;", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "null;", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_startingWithBuiltInIdentifier() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "library.getName();", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "library.getName();", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_true() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "true;", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "true;", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNonLabeledStatement_typeCast() {
-    ExpressionStatement statement = ParserTestCase.parse6("parseNonLabeledStatement", "double.NAN as num;", []);
+    ExpressionStatement statement = ParserTestCase.parse5("parseNonLabeledStatement", "double.NAN as num;", []);
     JUnitTestCase.assertNotNull(statement.expression);
   }
   void test_parseNormalFormalParameter_field_const_noType() {
-    FieldFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "const this.a)", []);
+    FieldFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "const this.a)", []);
     JUnitTestCase.assertNotNull(parameter.keyword);
     JUnitTestCase.assertNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_field_const_type() {
-    FieldFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "const A this.a)", []);
+    FieldFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "const A this.a)", []);
     JUnitTestCase.assertNotNull(parameter.keyword);
     JUnitTestCase.assertNotNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_field_final_noType() {
-    FieldFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "final this.a)", []);
+    FieldFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "final this.a)", []);
     JUnitTestCase.assertNotNull(parameter.keyword);
     JUnitTestCase.assertNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_field_final_type() {
-    FieldFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "final A this.a)", []);
+    FieldFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "final A this.a)", []);
     JUnitTestCase.assertNotNull(parameter.keyword);
     JUnitTestCase.assertNotNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_field_noType() {
-    FieldFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "this.a)", []);
+    FieldFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "this.a)", []);
     JUnitTestCase.assertNull(parameter.keyword);
     JUnitTestCase.assertNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_field_type() {
-    FieldFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "A this.a)", []);
+    FieldFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "A this.a)", []);
     JUnitTestCase.assertNull(parameter.keyword);
     JUnitTestCase.assertNotNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_field_var() {
-    FieldFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "var this.a)", []);
+    FieldFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "var this.a)", []);
     JUnitTestCase.assertNotNull(parameter.keyword);
     JUnitTestCase.assertNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_function_noType() {
-    FunctionTypedFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "a())", []);
+    FunctionTypedFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "a())", []);
     JUnitTestCase.assertNull(parameter.returnType);
     JUnitTestCase.assertNotNull(parameter.identifier);
     JUnitTestCase.assertNotNull(parameter.parameters);
   }
   void test_parseNormalFormalParameter_function_type() {
-    FunctionTypedFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "A a())", []);
+    FunctionTypedFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "A a())", []);
     JUnitTestCase.assertNotNull(parameter.returnType);
     JUnitTestCase.assertNotNull(parameter.identifier);
     JUnitTestCase.assertNotNull(parameter.parameters);
   }
   void test_parseNormalFormalParameter_function_void() {
-    FunctionTypedFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "void a())", []);
+    FunctionTypedFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "void a())", []);
     JUnitTestCase.assertNotNull(parameter.returnType);
     JUnitTestCase.assertNotNull(parameter.identifier);
     JUnitTestCase.assertNotNull(parameter.parameters);
   }
   void test_parseNormalFormalParameter_simple_const_noType() {
-    SimpleFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "const a)", []);
+    SimpleFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "const a)", []);
     JUnitTestCase.assertNotNull(parameter.keyword);
     JUnitTestCase.assertNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_simple_const_type() {
-    SimpleFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "const A a)", []);
+    SimpleFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "const A a)", []);
     JUnitTestCase.assertNotNull(parameter.keyword);
     JUnitTestCase.assertNotNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_simple_final_noType() {
-    SimpleFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "final a)", []);
+    SimpleFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "final a)", []);
     JUnitTestCase.assertNotNull(parameter.keyword);
     JUnitTestCase.assertNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_simple_final_type() {
-    SimpleFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "final A a)", []);
+    SimpleFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "final A a)", []);
     JUnitTestCase.assertNotNull(parameter.keyword);
     JUnitTestCase.assertNotNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_simple_noType() {
-    SimpleFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "a)", []);
+    SimpleFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "a)", []);
     JUnitTestCase.assertNull(parameter.keyword);
     JUnitTestCase.assertNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
   }
   void test_parseNormalFormalParameter_simple_type() {
-    SimpleFormalParameter parameter = ParserTestCase.parse6("parseNormalFormalParameter", "A a)", []);
+    SimpleFormalParameter parameter = ParserTestCase.parse5("parseNormalFormalParameter", "A a)", []);
     JUnitTestCase.assertNull(parameter.keyword);
     JUnitTestCase.assertNotNull(parameter.type);
     JUnitTestCase.assertNotNull(parameter.identifier);
@@ -2617,144 +2612,144 @@
     JUnitTestCase.assertNotNull(directive.semicolon);
   }
   void test_parsePostfixExpression_decrement() {
-    PostfixExpression expression = ParserTestCase.parse6("parsePostfixExpression", "i--", []);
+    PostfixExpression expression = ParserTestCase.parse5("parsePostfixExpression", "i--", []);
     JUnitTestCase.assertNotNull(expression.operand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.MINUS_MINUS, expression.operator.type);
   }
   void test_parsePostfixExpression_increment() {
-    PostfixExpression expression = ParserTestCase.parse6("parsePostfixExpression", "i++", []);
+    PostfixExpression expression = ParserTestCase.parse5("parsePostfixExpression", "i++", []);
     JUnitTestCase.assertNotNull(expression.operand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.PLUS_PLUS, expression.operator.type);
   }
   void test_parsePostfixExpression_none_indexExpression() {
-    IndexExpression expression = ParserTestCase.parse6("parsePostfixExpression", "a[0]", []);
+    IndexExpression expression = ParserTestCase.parse5("parsePostfixExpression", "a[0]", []);
     JUnitTestCase.assertNotNull(expression.array);
     JUnitTestCase.assertNotNull(expression.index);
   }
   void test_parsePostfixExpression_none_methodInvocation() {
-    MethodInvocation expression = ParserTestCase.parse6("parsePostfixExpression", "a.m()", []);
+    MethodInvocation expression = ParserTestCase.parse5("parsePostfixExpression", "a.m()", []);
     JUnitTestCase.assertNotNull(expression.target);
     JUnitTestCase.assertNotNull(expression.methodName);
     JUnitTestCase.assertNotNull(expression.argumentList);
   }
   void test_parsePostfixExpression_none_propertyAccess() {
-    PrefixedIdentifier expression = ParserTestCase.parse6("parsePostfixExpression", "a.b", []);
+    PrefixedIdentifier expression = ParserTestCase.parse5("parsePostfixExpression", "a.b", []);
     JUnitTestCase.assertNotNull(expression.prefix);
     JUnitTestCase.assertNotNull(expression.identifier);
   }
   void test_parsePrefixedIdentifier_noPrefix() {
     String lexeme = "bar";
-    SimpleIdentifier identifier = ParserTestCase.parse6("parsePrefixedIdentifier", lexeme, []);
+    SimpleIdentifier identifier = ParserTestCase.parse5("parsePrefixedIdentifier", lexeme, []);
     JUnitTestCase.assertNotNull(identifier.token);
     JUnitTestCase.assertEquals(lexeme, identifier.name);
   }
   void test_parsePrefixedIdentifier_prefix() {
     String lexeme = "foo.bar";
-    PrefixedIdentifier identifier = ParserTestCase.parse6("parsePrefixedIdentifier", lexeme, []);
+    PrefixedIdentifier identifier = ParserTestCase.parse5("parsePrefixedIdentifier", lexeme, []);
     JUnitTestCase.assertEquals("foo", identifier.prefix.name);
     JUnitTestCase.assertNotNull(identifier.period);
     JUnitTestCase.assertEquals("bar", identifier.identifier.name);
   }
   void test_parsePrimaryExpression_argumentDefinitionTest() {
-    ArgumentDefinitionTest expression = ParserTestCase.parse6("parseArgumentDefinitionTest", "?a", []);
+    ArgumentDefinitionTest expression = ParserTestCase.parse5("parseArgumentDefinitionTest", "?a", []);
     JUnitTestCase.assertNotNull(expression.question);
     JUnitTestCase.assertNotNull(expression.identifier);
   }
   void test_parsePrimaryExpression_const() {
-    InstanceCreationExpression expression = ParserTestCase.parse6("parsePrimaryExpression", "const A()", []);
+    InstanceCreationExpression expression = ParserTestCase.parse5("parsePrimaryExpression", "const A()", []);
     JUnitTestCase.assertNotNull(expression);
   }
   void test_parsePrimaryExpression_double() {
     String doubleLiteral = "3.2e4";
-    DoubleLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", doubleLiteral, []);
+    DoubleLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", doubleLiteral, []);
     JUnitTestCase.assertNotNull(literal.literal);
     JUnitTestCase.assertEquals(double.parse(doubleLiteral), literal.value);
   }
   void test_parsePrimaryExpression_false() {
-    BooleanLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", "false", []);
+    BooleanLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", "false", []);
     JUnitTestCase.assertNotNull(literal.literal);
     JUnitTestCase.assertFalse(literal.value);
   }
   void test_parsePrimaryExpression_function_arguments() {
-    FunctionExpression expression = ParserTestCase.parse6("parsePrimaryExpression", "(int i) => i + 1", []);
+    FunctionExpression expression = ParserTestCase.parse5("parsePrimaryExpression", "(int i) => i + 1", []);
     JUnitTestCase.assertNotNull(expression.parameters);
     JUnitTestCase.assertNotNull(expression.body);
   }
   void test_parsePrimaryExpression_function_noArguments() {
-    FunctionExpression expression = ParserTestCase.parse6("parsePrimaryExpression", "() => 42", []);
+    FunctionExpression expression = ParserTestCase.parse5("parsePrimaryExpression", "() => 42", []);
     JUnitTestCase.assertNotNull(expression.parameters);
     JUnitTestCase.assertNotNull(expression.body);
   }
   void test_parsePrimaryExpression_hex() {
     String hexLiteral = "3F";
-    IntegerLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", "0x${hexLiteral}", []);
+    IntegerLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", "0x${hexLiteral}", []);
     JUnitTestCase.assertNotNull(literal.literal);
     JUnitTestCase.assertEquals(int.parse(hexLiteral, radix: 16), literal.value);
   }
   void test_parsePrimaryExpression_identifier() {
-    SimpleIdentifier identifier = ParserTestCase.parse6("parsePrimaryExpression", "a", []);
+    SimpleIdentifier identifier = ParserTestCase.parse5("parsePrimaryExpression", "a", []);
     JUnitTestCase.assertNotNull(identifier);
   }
   void test_parsePrimaryExpression_int() {
     String intLiteral = "472";
-    IntegerLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", intLiteral, []);
+    IntegerLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", intLiteral, []);
     JUnitTestCase.assertNotNull(literal.literal);
     JUnitTestCase.assertEquals(int.parse(intLiteral), literal.value);
   }
   void test_parsePrimaryExpression_listLiteral() {
-    ListLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", "[ ]", []);
+    ListLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", "[ ]", []);
     JUnitTestCase.assertNotNull(literal);
   }
   void test_parsePrimaryExpression_listLiteral_index() {
-    ListLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", "[]", []);
+    ListLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", "[]", []);
     JUnitTestCase.assertNotNull(literal);
   }
   void test_parsePrimaryExpression_listLiteral_typed() {
-    ListLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", "<A>[ ]", []);
+    ListLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", "<A>[ ]", []);
     JUnitTestCase.assertNotNull(literal.typeArguments);
     EngineTestCase.assertSize(1, literal.typeArguments.arguments);
   }
   void test_parsePrimaryExpression_mapLiteral() {
-    MapLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", "{}", []);
+    MapLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", "{}", []);
     JUnitTestCase.assertNotNull(literal);
   }
   void test_parsePrimaryExpression_mapLiteral_typed() {
-    MapLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", "<A>{}", []);
+    MapLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", "<A>{}", []);
     JUnitTestCase.assertNotNull(literal.typeArguments);
     EngineTestCase.assertSize(1, literal.typeArguments.arguments);
   }
   void test_parsePrimaryExpression_new() {
-    InstanceCreationExpression expression = ParserTestCase.parse6("parsePrimaryExpression", "new A()", []);
+    InstanceCreationExpression expression = ParserTestCase.parse5("parsePrimaryExpression", "new A()", []);
     JUnitTestCase.assertNotNull(expression);
   }
   void test_parsePrimaryExpression_null() {
-    NullLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", "null", []);
+    NullLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", "null", []);
     JUnitTestCase.assertNotNull(literal.literal);
   }
   void test_parsePrimaryExpression_parenthesized() {
-    ParenthesizedExpression expression = ParserTestCase.parse6("parsePrimaryExpression", "()", []);
+    ParenthesizedExpression expression = ParserTestCase.parse5("parsePrimaryExpression", "()", []);
     JUnitTestCase.assertNotNull(expression);
   }
   void test_parsePrimaryExpression_string() {
-    SimpleStringLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", "\"string\"", []);
+    SimpleStringLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", "\"string\"", []);
     JUnitTestCase.assertFalse(literal.isMultiline());
     JUnitTestCase.assertEquals("string", literal.value);
   }
   void test_parsePrimaryExpression_super() {
-    PropertyAccess propertyAccess = ParserTestCase.parse6("parsePrimaryExpression", "super.x", []);
+    PropertyAccess propertyAccess = ParserTestCase.parse5("parsePrimaryExpression", "super.x", []);
     JUnitTestCase.assertTrue(propertyAccess.target is SuperExpression);
     JUnitTestCase.assertNotNull(propertyAccess.operator);
     JUnitTestCase.assertEquals(TokenType.PERIOD, propertyAccess.operator.type);
     JUnitTestCase.assertNotNull(propertyAccess.propertyName);
   }
   void test_parsePrimaryExpression_this() {
-    ThisExpression expression = ParserTestCase.parse6("parsePrimaryExpression", "this", []);
+    ThisExpression expression = ParserTestCase.parse5("parsePrimaryExpression", "this", []);
     JUnitTestCase.assertNotNull(expression.keyword);
   }
   void test_parsePrimaryExpression_true() {
-    BooleanLiteral literal = ParserTestCase.parse6("parsePrimaryExpression", "true", []);
+    BooleanLiteral literal = ParserTestCase.parse5("parsePrimaryExpression", "true", []);
     JUnitTestCase.assertNotNull(literal.literal);
     JUnitTestCase.assertTrue(literal.value);
   }
@@ -2762,72 +2757,76 @@
     JUnitTestCase.assertNotNull(new Parser(null, null));
   }
   void test_parseRedirectingConstructorInvocation_named() {
-    RedirectingConstructorInvocation invocation = ParserTestCase.parse6("parseRedirectingConstructorInvocation", "this.a()", []);
+    RedirectingConstructorInvocation invocation = ParserTestCase.parse5("parseRedirectingConstructorInvocation", "this.a()", []);
     JUnitTestCase.assertNotNull(invocation.argumentList);
     JUnitTestCase.assertNotNull(invocation.constructorName);
     JUnitTestCase.assertNotNull(invocation.keyword);
     JUnitTestCase.assertNotNull(invocation.period);
   }
   void test_parseRedirectingConstructorInvocation_unnamed() {
-    RedirectingConstructorInvocation invocation = ParserTestCase.parse6("parseRedirectingConstructorInvocation", "this()", []);
+    RedirectingConstructorInvocation invocation = ParserTestCase.parse5("parseRedirectingConstructorInvocation", "this()", []);
     JUnitTestCase.assertNotNull(invocation.argumentList);
     JUnitTestCase.assertNull(invocation.constructorName);
     JUnitTestCase.assertNotNull(invocation.keyword);
     JUnitTestCase.assertNull(invocation.period);
   }
   void test_parseRelationalExpression_as() {
-    AsExpression expression = ParserTestCase.parse6("parseRelationalExpression", "x as Y", []);
+    AsExpression expression = ParserTestCase.parse5("parseRelationalExpression", "x as Y", []);
     JUnitTestCase.assertNotNull(expression.expression);
     JUnitTestCase.assertNotNull(expression.asOperator);
     JUnitTestCase.assertNotNull(expression.type);
   }
   void test_parseRelationalExpression_is() {
-    IsExpression expression = ParserTestCase.parse6("parseRelationalExpression", "x is y", []);
+    IsExpression expression = ParserTestCase.parse5("parseRelationalExpression", "x is y", []);
     JUnitTestCase.assertNotNull(expression.expression);
     JUnitTestCase.assertNotNull(expression.isOperator);
     JUnitTestCase.assertNull(expression.notOperator);
     JUnitTestCase.assertNotNull(expression.type);
   }
   void test_parseRelationalExpression_isNot() {
-    IsExpression expression = ParserTestCase.parse6("parseRelationalExpression", "x is! y", []);
+    IsExpression expression = ParserTestCase.parse5("parseRelationalExpression", "x is! y", []);
     JUnitTestCase.assertNotNull(expression.expression);
     JUnitTestCase.assertNotNull(expression.isOperator);
     JUnitTestCase.assertNotNull(expression.notOperator);
     JUnitTestCase.assertNotNull(expression.type);
   }
   void test_parseRelationalExpression_normal() {
-    BinaryExpression expression = ParserTestCase.parse6("parseRelationalExpression", "x < y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseRelationalExpression", "x < y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.LT, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseRelationalExpression_super() {
-    BinaryExpression expression = ParserTestCase.parse6("parseRelationalExpression", "super < y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseRelationalExpression", "super < y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.LT, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
+  void test_parseRethrowExpression() {
+    RethrowExpression expression = ParserTestCase.parse5("parseRethrowExpression", "rethrow;", []);
+    JUnitTestCase.assertNotNull(expression.keyword);
+  }
   void test_parseReturnStatement_noValue() {
-    ReturnStatement statement = ParserTestCase.parse6("parseReturnStatement", "return;", []);
+    ReturnStatement statement = ParserTestCase.parse5("parseReturnStatement", "return;", []);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNull(statement.expression);
     JUnitTestCase.assertNotNull(statement.semicolon);
   }
   void test_parseReturnStatement_value() {
-    ReturnStatement statement = ParserTestCase.parse6("parseReturnStatement", "return x;", []);
+    ReturnStatement statement = ParserTestCase.parse5("parseReturnStatement", "return x;", []);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNotNull(statement.expression);
     JUnitTestCase.assertNotNull(statement.semicolon);
   }
   void test_parseReturnType_nonVoid() {
-    TypeName typeName = ParserTestCase.parse6("parseReturnType", "A<B>", []);
+    TypeName typeName = ParserTestCase.parse5("parseReturnType", "A<B>", []);
     JUnitTestCase.assertNotNull(typeName.name);
     JUnitTestCase.assertNotNull(typeName.typeArguments);
   }
   void test_parseReturnType_void() {
-    TypeName typeName = ParserTestCase.parse6("parseReturnType", "void", []);
+    TypeName typeName = ParserTestCase.parse5("parseReturnType", "void", []);
     JUnitTestCase.assertNotNull(typeName.name);
     JUnitTestCase.assertNull(typeName.typeArguments);
   }
@@ -2861,14 +2860,14 @@
     JUnitTestCase.assertEquals(returnType, method.returnType);
   }
   void test_parseShiftExpression_normal() {
-    BinaryExpression expression = ParserTestCase.parse6("parseShiftExpression", "x << y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseShiftExpression", "x << y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.LT_LT, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.rightOperand);
   }
   void test_parseShiftExpression_super() {
-    BinaryExpression expression = ParserTestCase.parse6("parseShiftExpression", "super << y", []);
+    BinaryExpression expression = ParserTestCase.parse5("parseShiftExpression", "super << y", []);
     JUnitTestCase.assertNotNull(expression.leftOperand);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.LT_LT, expression.operator.type);
@@ -2876,32 +2875,32 @@
   }
   void test_parseSimpleIdentifier_builtInIdentifier() {
     String lexeme = "as";
-    SimpleIdentifier identifier = ParserTestCase.parse6("parseSimpleIdentifier", lexeme, []);
+    SimpleIdentifier identifier = ParserTestCase.parse5("parseSimpleIdentifier", lexeme, []);
     JUnitTestCase.assertNotNull(identifier.token);
     JUnitTestCase.assertEquals(lexeme, identifier.name);
   }
   void test_parseSimpleIdentifier_normalIdentifier() {
     String lexeme = "foo";
-    SimpleIdentifier identifier = ParserTestCase.parse6("parseSimpleIdentifier", lexeme, []);
+    SimpleIdentifier identifier = ParserTestCase.parse5("parseSimpleIdentifier", lexeme, []);
     JUnitTestCase.assertNotNull(identifier.token);
     JUnitTestCase.assertEquals(lexeme, identifier.name);
   }
   void test_parseSimpleIdentifier1_normalIdentifier() {
   }
   void test_parseStatement_functionDeclaration() {
-    FunctionDeclarationStatement statement = ParserTestCase.parse6("parseStatement", "int f(a, b) {};", []);
+    FunctionDeclarationStatement statement = ParserTestCase.parse5("parseStatement", "int f(a, b) {};", []);
     JUnitTestCase.assertNotNull(statement.functionDeclaration);
   }
   void test_parseStatement_mulipleLabels() {
-    LabeledStatement statement = ParserTestCase.parse6("parseStatement", "l: m: return x;", []);
+    LabeledStatement statement = ParserTestCase.parse5("parseStatement", "l: m: return x;", []);
     EngineTestCase.assertSize(2, statement.labels);
     JUnitTestCase.assertNotNull(statement.statement);
   }
   void test_parseStatement_noLabels() {
-    ParserTestCase.parse6("parseStatement", "return x;", []);
+    ParserTestCase.parse5("parseStatement", "return x;", []);
   }
   void test_parseStatement_singleLabel() {
-    LabeledStatement statement = ParserTestCase.parse6("parseStatement", "l: return x;", []);
+    LabeledStatement statement = ParserTestCase.parse5("parseStatement", "l: return x;", []);
     EngineTestCase.assertSize(1, statement.labels);
     JUnitTestCase.assertNotNull(statement.statement);
   }
@@ -2914,7 +2913,7 @@
     EngineTestCase.assertSize(1, statements);
   }
   void test_parseStringLiteral_adjacent() {
-    AdjacentStrings literal = ParserTestCase.parse6("parseStringLiteral", "'a' 'b'", []);
+    AdjacentStrings literal = ParserTestCase.parse5("parseStringLiteral", "'a' 'b'", []);
     NodeList<StringLiteral> strings2 = literal.strings;
     EngineTestCase.assertSize(2, strings2);
     StringLiteral firstString = strings2[0];
@@ -2923,7 +2922,7 @@
     JUnitTestCase.assertEquals("b", ((secondString as SimpleStringLiteral)).value);
   }
   void test_parseStringLiteral_interpolated() {
-    StringInterpolation literal = ParserTestCase.parse6("parseStringLiteral", "'a \${b} c \$this d'", []);
+    StringInterpolation literal = ParserTestCase.parse5("parseStringLiteral", "'a \${b} c \$this d'", []);
     NodeList<InterpolationElement> elements2 = literal.elements;
     EngineTestCase.assertSize(5, elements2);
     JUnitTestCase.assertTrue(elements2[0] is InterpolationString);
@@ -2933,26 +2932,26 @@
     JUnitTestCase.assertTrue(elements2[4] is InterpolationString);
   }
   void test_parseStringLiteral_single() {
-    SimpleStringLiteral literal = ParserTestCase.parse6("parseStringLiteral", "'a'", []);
+    SimpleStringLiteral literal = ParserTestCase.parse5("parseStringLiteral", "'a'", []);
     JUnitTestCase.assertNotNull(literal.literal);
     JUnitTestCase.assertEquals("a", literal.value);
   }
   void test_parseSuperConstructorInvocation_named() {
-    SuperConstructorInvocation invocation = ParserTestCase.parse6("parseSuperConstructorInvocation", "super.a()", []);
+    SuperConstructorInvocation invocation = ParserTestCase.parse5("parseSuperConstructorInvocation", "super.a()", []);
     JUnitTestCase.assertNotNull(invocation.argumentList);
     JUnitTestCase.assertNotNull(invocation.constructorName);
     JUnitTestCase.assertNotNull(invocation.keyword);
     JUnitTestCase.assertNotNull(invocation.period);
   }
   void test_parseSuperConstructorInvocation_unnamed() {
-    SuperConstructorInvocation invocation = ParserTestCase.parse6("parseSuperConstructorInvocation", "super()", []);
+    SuperConstructorInvocation invocation = ParserTestCase.parse5("parseSuperConstructorInvocation", "super()", []);
     JUnitTestCase.assertNotNull(invocation.argumentList);
     JUnitTestCase.assertNull(invocation.constructorName);
     JUnitTestCase.assertNotNull(invocation.keyword);
     JUnitTestCase.assertNull(invocation.period);
   }
   void test_parseSwitchStatement_case() {
-    SwitchStatement statement = ParserTestCase.parse6("parseSwitchStatement", "switch (a) {case 1: return 'I';}", []);
+    SwitchStatement statement = ParserTestCase.parse5("parseSwitchStatement", "switch (a) {case 1: return 'I';}", []);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.expression);
@@ -2962,7 +2961,7 @@
     JUnitTestCase.assertNotNull(statement.rightBracket);
   }
   void test_parseSwitchStatement_empty() {
-    SwitchStatement statement = ParserTestCase.parse6("parseSwitchStatement", "switch (a) {}", []);
+    SwitchStatement statement = ParserTestCase.parse5("parseSwitchStatement", "switch (a) {}", []);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.expression);
@@ -2972,7 +2971,7 @@
     JUnitTestCase.assertNotNull(statement.rightBracket);
   }
   void test_parseSwitchStatement_labeledCase() {
-    SwitchStatement statement = ParserTestCase.parse6("parseSwitchStatement", "switch (a) {l1: l2: l3: case(1):}", []);
+    SwitchStatement statement = ParserTestCase.parse5("parseSwitchStatement", "switch (a) {l1: l2: l3: case(1):}", []);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.expression);
@@ -2983,7 +2982,7 @@
     JUnitTestCase.assertNotNull(statement.rightBracket);
   }
   void test_parseSwitchStatement_labeledStatementInCase() {
-    SwitchStatement statement = ParserTestCase.parse6("parseSwitchStatement", "switch (a) {case 0: f(); l1: g(); break;}", []);
+    SwitchStatement statement = ParserTestCase.parse5("parseSwitchStatement", "switch (a) {case 0: f(); l1: g(); break;}", []);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.expression);
@@ -2993,28 +2992,18 @@
     EngineTestCase.assertSize(3, statement.members[0].statements);
     JUnitTestCase.assertNotNull(statement.rightBracket);
   }
-  void test_parseThrowExpression_expression() {
-    ThrowExpression statement = ParserTestCase.parse6("parseThrowExpression", "throw x;", []);
-    JUnitTestCase.assertNotNull(statement.keyword);
-    JUnitTestCase.assertNotNull(statement.expression);
+  void test_parseThrowExpression() {
+    ThrowExpression expression = ParserTestCase.parse5("parseThrowExpression", "throw x;", []);
+    JUnitTestCase.assertNotNull(expression.keyword);
+    JUnitTestCase.assertNotNull(expression.expression);
   }
-  void test_parseThrowExpression_noExpression() {
-    ThrowExpression statement = ParserTestCase.parse6("parseThrowExpression", "throw;", []);
-    JUnitTestCase.assertNotNull(statement.keyword);
-    JUnitTestCase.assertNull(statement.expression);
-  }
-  void test_parseThrowExpressionWithoutCascade_expression() {
-    ThrowExpression statement = ParserTestCase.parse6("parseThrowExpressionWithoutCascade", "throw x;", []);
-    JUnitTestCase.assertNotNull(statement.keyword);
-    JUnitTestCase.assertNotNull(statement.expression);
-  }
-  void test_parseThrowExpressionWithoutCascade_noExpression() {
-    ThrowExpression statement = ParserTestCase.parse6("parseThrowExpressionWithoutCascade", "throw;", []);
-    JUnitTestCase.assertNotNull(statement.keyword);
-    JUnitTestCase.assertNull(statement.expression);
+  void test_parseThrowExpressionWithoutCascade() {
+    ThrowExpression expression = ParserTestCase.parse5("parseThrowExpressionWithoutCascade", "throw x;", []);
+    JUnitTestCase.assertNotNull(expression.keyword);
+    JUnitTestCase.assertNotNull(expression.expression);
   }
   void test_parseTryStatement_catch() {
-    TryStatement statement = ParserTestCase.parse6("parseTryStatement", "try {} catch (e) {}", []);
+    TryStatement statement = ParserTestCase.parse5("parseTryStatement", "try {} catch (e) {}", []);
     JUnitTestCase.assertNotNull(statement.tryKeyword);
     JUnitTestCase.assertNotNull(statement.body);
     NodeList<CatchClause> catchClauses2 = statement.catchClauses;
@@ -3031,7 +3020,7 @@
     JUnitTestCase.assertNull(statement.finallyClause);
   }
   void test_parseTryStatement_catch_finally() {
-    TryStatement statement = ParserTestCase.parse6("parseTryStatement", "try {} catch (e, s) {} finally {}", []);
+    TryStatement statement = ParserTestCase.parse5("parseTryStatement", "try {} catch (e, s) {} finally {}", []);
     JUnitTestCase.assertNotNull(statement.tryKeyword);
     JUnitTestCase.assertNotNull(statement.body);
     NodeList<CatchClause> catchClauses3 = statement.catchClauses;
@@ -3048,7 +3037,7 @@
     JUnitTestCase.assertNotNull(statement.finallyClause);
   }
   void test_parseTryStatement_finally() {
-    TryStatement statement = ParserTestCase.parse6("parseTryStatement", "try {} finally {}", []);
+    TryStatement statement = ParserTestCase.parse5("parseTryStatement", "try {} finally {}", []);
     JUnitTestCase.assertNotNull(statement.tryKeyword);
     JUnitTestCase.assertNotNull(statement.body);
     EngineTestCase.assertSize(0, statement.catchClauses);
@@ -3056,7 +3045,7 @@
     JUnitTestCase.assertNotNull(statement.finallyClause);
   }
   void test_parseTryStatement_multiple() {
-    TryStatement statement = ParserTestCase.parse6("parseTryStatement", "try {} on NPE catch (e) {} on Error {} catch (e) {}", []);
+    TryStatement statement = ParserTestCase.parse5("parseTryStatement", "try {} on NPE catch (e) {} on Error {} catch (e) {}", []);
     JUnitTestCase.assertNotNull(statement.tryKeyword);
     JUnitTestCase.assertNotNull(statement.body);
     EngineTestCase.assertSize(3, statement.catchClauses);
@@ -3064,7 +3053,7 @@
     JUnitTestCase.assertNull(statement.finallyClause);
   }
   void test_parseTryStatement_on() {
-    TryStatement statement = ParserTestCase.parse6("parseTryStatement", "try {} on Error {}", []);
+    TryStatement statement = ParserTestCase.parse5("parseTryStatement", "try {} on Error {}", []);
     JUnitTestCase.assertNotNull(statement.tryKeyword);
     JUnitTestCase.assertNotNull(statement.body);
     NodeList<CatchClause> catchClauses4 = statement.catchClauses;
@@ -3081,7 +3070,7 @@
     JUnitTestCase.assertNull(statement.finallyClause);
   }
   void test_parseTryStatement_on_catch() {
-    TryStatement statement = ParserTestCase.parse6("parseTryStatement", "try {} on Error catch (e, s) {}", []);
+    TryStatement statement = ParserTestCase.parse5("parseTryStatement", "try {} on Error catch (e, s) {}", []);
     JUnitTestCase.assertNotNull(statement.tryKeyword);
     JUnitTestCase.assertNotNull(statement.body);
     NodeList<CatchClause> catchClauses5 = statement.catchClauses;
@@ -3098,7 +3087,7 @@
     JUnitTestCase.assertNull(statement.finallyClause);
   }
   void test_parseTryStatement_on_catch_finally() {
-    TryStatement statement = ParserTestCase.parse6("parseTryStatement", "try {} on Error catch (e, s) {} finally {}", []);
+    TryStatement statement = ParserTestCase.parse5("parseTryStatement", "try {} on Error catch (e, s) {} finally {}", []);
     JUnitTestCase.assertNotNull(statement.tryKeyword);
     JUnitTestCase.assertNotNull(statement.body);
     NodeList<CatchClause> catchClauses6 = statement.catchClauses;
@@ -3191,13 +3180,13 @@
     JUnitTestCase.assertNull(typeAlias.typeParameters);
   }
   void test_parseTypeArgumentList_multiple() {
-    TypeArgumentList argumentList = ParserTestCase.parse6("parseTypeArgumentList", "<int, int, int>", []);
+    TypeArgumentList argumentList = ParserTestCase.parse5("parseTypeArgumentList", "<int, int, int>", []);
     JUnitTestCase.assertNotNull(argumentList.leftBracket);
     EngineTestCase.assertSize(3, argumentList.arguments);
     JUnitTestCase.assertNotNull(argumentList.rightBracket);
   }
   void test_parseTypeArgumentList_nested() {
-    TypeArgumentList argumentList = ParserTestCase.parse6("parseTypeArgumentList", "<A<B>>", []);
+    TypeArgumentList argumentList = ParserTestCase.parse5("parseTypeArgumentList", "<A<B>>", []);
     JUnitTestCase.assertNotNull(argumentList.leftBracket);
     EngineTestCase.assertSize(1, argumentList.arguments);
     TypeName argument = argumentList.arguments[0];
@@ -3208,65 +3197,65 @@
     JUnitTestCase.assertNotNull(argumentList.rightBracket);
   }
   void test_parseTypeArgumentList_single() {
-    TypeArgumentList argumentList = ParserTestCase.parse6("parseTypeArgumentList", "<int>", []);
+    TypeArgumentList argumentList = ParserTestCase.parse5("parseTypeArgumentList", "<int>", []);
     JUnitTestCase.assertNotNull(argumentList.leftBracket);
     EngineTestCase.assertSize(1, argumentList.arguments);
     JUnitTestCase.assertNotNull(argumentList.rightBracket);
   }
   void test_parseTypeName_parameterized() {
-    TypeName typeName = ParserTestCase.parse6("parseTypeName", "List<int>", []);
+    TypeName typeName = ParserTestCase.parse5("parseTypeName", "List<int>", []);
     JUnitTestCase.assertNotNull(typeName.name);
     JUnitTestCase.assertNotNull(typeName.typeArguments);
   }
   void test_parseTypeName_simple() {
-    TypeName typeName = ParserTestCase.parse6("parseTypeName", "int", []);
+    TypeName typeName = ParserTestCase.parse5("parseTypeName", "int", []);
     JUnitTestCase.assertNotNull(typeName.name);
     JUnitTestCase.assertNull(typeName.typeArguments);
   }
   void test_parseTypeParameter_bounded() {
-    TypeParameter parameter = ParserTestCase.parse6("parseTypeParameter", "A extends B", []);
+    TypeParameter parameter = ParserTestCase.parse5("parseTypeParameter", "A extends B", []);
     JUnitTestCase.assertNotNull(parameter.bound);
     JUnitTestCase.assertNotNull(parameter.keyword);
     JUnitTestCase.assertNotNull(parameter.name);
   }
   void test_parseTypeParameter_simple() {
-    TypeParameter parameter = ParserTestCase.parse6("parseTypeParameter", "A", []);
+    TypeParameter parameter = ParserTestCase.parse5("parseTypeParameter", "A", []);
     JUnitTestCase.assertNull(parameter.bound);
     JUnitTestCase.assertNull(parameter.keyword);
     JUnitTestCase.assertNotNull(parameter.name);
   }
   void test_parseTypeParameterList_multiple() {
-    TypeParameterList parameterList = ParserTestCase.parse6("parseTypeParameterList", "<A, B extends C, D>", []);
+    TypeParameterList parameterList = ParserTestCase.parse5("parseTypeParameterList", "<A, B extends C, D>", []);
     JUnitTestCase.assertNotNull(parameterList.leftBracket);
     JUnitTestCase.assertNotNull(parameterList.rightBracket);
     EngineTestCase.assertSize(3, parameterList.typeParameters);
   }
   void test_parseTypeParameterList_parameterizedWithTrailingEquals() {
-    TypeParameterList parameterList = ParserTestCase.parse6("parseTypeParameterList", "<A extends B<E>>=", []);
+    TypeParameterList parameterList = ParserTestCase.parse5("parseTypeParameterList", "<A extends B<E>>=", []);
     JUnitTestCase.assertNotNull(parameterList.leftBracket);
     JUnitTestCase.assertNotNull(parameterList.rightBracket);
     EngineTestCase.assertSize(1, parameterList.typeParameters);
   }
   void test_parseTypeParameterList_single() {
-    TypeParameterList parameterList = ParserTestCase.parse6("parseTypeParameterList", "<A>", []);
+    TypeParameterList parameterList = ParserTestCase.parse5("parseTypeParameterList", "<A>", []);
     JUnitTestCase.assertNotNull(parameterList.leftBracket);
     JUnitTestCase.assertNotNull(parameterList.rightBracket);
     EngineTestCase.assertSize(1, parameterList.typeParameters);
   }
   void test_parseTypeParameterList_withTrailingEquals() {
-    TypeParameterList parameterList = ParserTestCase.parse6("parseTypeParameterList", "<A>=", []);
+    TypeParameterList parameterList = ParserTestCase.parse5("parseTypeParameterList", "<A>=", []);
     JUnitTestCase.assertNotNull(parameterList.leftBracket);
     JUnitTestCase.assertNotNull(parameterList.rightBracket);
     EngineTestCase.assertSize(1, parameterList.typeParameters);
   }
   void test_parseUnaryExpression_decrement_normal() {
-    PrefixExpression expression = ParserTestCase.parse6("parseUnaryExpression", "--x", []);
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "--x", []);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.MINUS_MINUS, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.operand);
   }
   void test_parseUnaryExpression_decrement_super() {
-    PrefixExpression expression = ParserTestCase.parse6("parseUnaryExpression", "--super", []);
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "--super", []);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.MINUS, expression.operator.type);
     Expression innerExpression = expression.operand;
@@ -3277,138 +3266,165 @@
     JUnitTestCase.assertEquals(TokenType.MINUS, operand.operator.type);
     JUnitTestCase.assertNotNull(operand.operand);
   }
+  void test_parseUnaryExpression_decrement_super_propertyAccess() {
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "--super.x", []);
+    JUnitTestCase.assertNotNull(expression.operator);
+    JUnitTestCase.assertEquals(TokenType.MINUS_MINUS, expression.operator.type);
+    JUnitTestCase.assertNotNull(expression.operand);
+    PropertyAccess operand4 = expression.operand as PropertyAccess;
+    JUnitTestCase.assertTrue(operand4.target is SuperExpression);
+    JUnitTestCase.assertEquals("x", operand4.propertyName.name);
+  }
   void test_parseUnaryExpression_increment_normal() {
-    PrefixExpression expression = ParserTestCase.parse6("parseUnaryExpression", "++x", []);
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "++x", []);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.PLUS_PLUS, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.operand);
   }
+  void test_parseUnaryExpression_increment_super_index() {
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "++super[0]", []);
+    JUnitTestCase.assertNotNull(expression.operator);
+    JUnitTestCase.assertEquals(TokenType.PLUS_PLUS, expression.operator.type);
+    JUnitTestCase.assertNotNull(expression.operand);
+    IndexExpression operand5 = expression.operand as IndexExpression;
+    JUnitTestCase.assertTrue(operand5.realTarget is SuperExpression);
+    JUnitTestCase.assertTrue(operand5.index is IntegerLiteral);
+  }
+  void test_parseUnaryExpression_increment_super_propertyAccess() {
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "++super.x", []);
+    JUnitTestCase.assertNotNull(expression.operator);
+    JUnitTestCase.assertEquals(TokenType.PLUS_PLUS, expression.operator.type);
+    JUnitTestCase.assertNotNull(expression.operand);
+    PropertyAccess operand6 = expression.operand as PropertyAccess;
+    JUnitTestCase.assertTrue(operand6.target is SuperExpression);
+    JUnitTestCase.assertEquals("x", operand6.propertyName.name);
+  }
   void test_parseUnaryExpression_minus_normal() {
-    PrefixExpression expression = ParserTestCase.parse6("parseUnaryExpression", "-x", []);
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "-x", []);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.MINUS, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.operand);
   }
   void test_parseUnaryExpression_minus_super() {
-    PrefixExpression expression = ParserTestCase.parse6("parseUnaryExpression", "-super", []);
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "-super", []);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.MINUS, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.operand);
   }
   void test_parseUnaryExpression_not_normal() {
-    PrefixExpression expression = ParserTestCase.parse6("parseUnaryExpression", "!x", []);
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "!x", []);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.BANG, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.operand);
   }
   void test_parseUnaryExpression_not_super() {
-    PrefixExpression expression = ParserTestCase.parse6("parseUnaryExpression", "!super", []);
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "!super", []);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.BANG, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.operand);
   }
   void test_parseUnaryExpression_tilda_normal() {
-    PrefixExpression expression = ParserTestCase.parse6("parseUnaryExpression", "~x", []);
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "~x", []);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.TILDE, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.operand);
   }
   void test_parseUnaryExpression_tilda_super() {
-    PrefixExpression expression = ParserTestCase.parse6("parseUnaryExpression", "~super", []);
+    PrefixExpression expression = ParserTestCase.parse5("parseUnaryExpression", "~super", []);
     JUnitTestCase.assertNotNull(expression.operator);
     JUnitTestCase.assertEquals(TokenType.TILDE, expression.operator.type);
     JUnitTestCase.assertNotNull(expression.operand);
   }
   void test_parseVariableDeclaration_equals() {
-    VariableDeclaration declaration = ParserTestCase.parse6("parseVariableDeclaration", "a = b", []);
+    VariableDeclaration declaration = ParserTestCase.parse5("parseVariableDeclaration", "a = b", []);
     JUnitTestCase.assertNotNull(declaration.name);
     JUnitTestCase.assertNotNull(declaration.equals);
     JUnitTestCase.assertNotNull(declaration.initializer);
   }
   void test_parseVariableDeclaration_noEquals() {
-    VariableDeclaration declaration = ParserTestCase.parse6("parseVariableDeclaration", "a", []);
+    VariableDeclaration declaration = ParserTestCase.parse5("parseVariableDeclaration", "a", []);
     JUnitTestCase.assertNotNull(declaration.name);
     JUnitTestCase.assertNull(declaration.equals);
     JUnitTestCase.assertNull(declaration.initializer);
   }
   void test_parseVariableDeclarationList_const_noType() {
-    VariableDeclarationList declarationList = ParserTestCase.parse6("parseVariableDeclarationList", "const a", []);
+    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [emptyCommentAndMetadata()], "const a");
     JUnitTestCase.assertNotNull(declarationList.keyword);
     JUnitTestCase.assertNull(declarationList.type);
     EngineTestCase.assertSize(1, declarationList.variables);
   }
   void test_parseVariableDeclarationList_const_type() {
-    VariableDeclarationList declarationList = ParserTestCase.parse6("parseVariableDeclarationList", "const A a", []);
+    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [emptyCommentAndMetadata()], "const A a");
     JUnitTestCase.assertNotNull(declarationList.keyword);
     JUnitTestCase.assertNotNull(declarationList.type);
     EngineTestCase.assertSize(1, declarationList.variables);
   }
   void test_parseVariableDeclarationList_final_noType() {
-    VariableDeclarationList declarationList = ParserTestCase.parse6("parseVariableDeclarationList", "final a", []);
+    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [emptyCommentAndMetadata()], "final a");
     JUnitTestCase.assertNotNull(declarationList.keyword);
     JUnitTestCase.assertNull(declarationList.type);
     EngineTestCase.assertSize(1, declarationList.variables);
   }
   void test_parseVariableDeclarationList_final_type() {
-    VariableDeclarationList declarationList = ParserTestCase.parse6("parseVariableDeclarationList", "final A a", []);
+    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [emptyCommentAndMetadata()], "final A a");
     JUnitTestCase.assertNotNull(declarationList.keyword);
     JUnitTestCase.assertNotNull(declarationList.type);
     EngineTestCase.assertSize(1, declarationList.variables);
   }
   void test_parseVariableDeclarationList_type_multiple() {
-    VariableDeclarationList declarationList = ParserTestCase.parse6("parseVariableDeclarationList", "A a, b, c", []);
+    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [emptyCommentAndMetadata()], "A a, b, c");
     JUnitTestCase.assertNull(declarationList.keyword);
     JUnitTestCase.assertNotNull(declarationList.type);
     EngineTestCase.assertSize(3, declarationList.variables);
   }
   void test_parseVariableDeclarationList_type_single() {
-    VariableDeclarationList declarationList = ParserTestCase.parse6("parseVariableDeclarationList", "A a", []);
+    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [emptyCommentAndMetadata()], "A a");
     JUnitTestCase.assertNull(declarationList.keyword);
     JUnitTestCase.assertNotNull(declarationList.type);
     EngineTestCase.assertSize(1, declarationList.variables);
   }
   void test_parseVariableDeclarationList_var_multiple() {
-    VariableDeclarationList declarationList = ParserTestCase.parse6("parseVariableDeclarationList", "var a, b, c", []);
+    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [emptyCommentAndMetadata()], "var a, b, c");
     JUnitTestCase.assertNotNull(declarationList.keyword);
     JUnitTestCase.assertNull(declarationList.type);
     EngineTestCase.assertSize(3, declarationList.variables);
   }
   void test_parseVariableDeclarationList_var_single() {
-    VariableDeclarationList declarationList = ParserTestCase.parse6("parseVariableDeclarationList", "var a", []);
+    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [emptyCommentAndMetadata()], "var a");
     JUnitTestCase.assertNotNull(declarationList.keyword);
     JUnitTestCase.assertNull(declarationList.type);
     EngineTestCase.assertSize(1, declarationList.variables);
   }
   void test_parseVariableDeclarationList2_type() {
     TypeName type = new TypeName.full(new SimpleIdentifier.full(null), null);
-    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [null, type], "a");
+    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [emptyCommentAndMetadata(), null, type], "a");
     JUnitTestCase.assertNull(declarationList.keyword);
     JUnitTestCase.assertEquals(type, declarationList.type);
     EngineTestCase.assertSize(1, declarationList.variables);
   }
   void test_parseVariableDeclarationList2_var() {
     Token keyword = TokenFactory.token(Keyword.VAR);
-    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [keyword, null], "a, b, c");
+    VariableDeclarationList declarationList = ParserTestCase.parse("parseVariableDeclarationList", <Object> [emptyCommentAndMetadata(), keyword, null], "a, b, c");
     JUnitTestCase.assertEquals(keyword, declarationList.keyword);
     JUnitTestCase.assertNull(declarationList.type);
     EngineTestCase.assertSize(3, declarationList.variables);
   }
   void test_parseVariableDeclarationStatement_multiple() {
-    VariableDeclarationStatement statement = ParserTestCase.parse6("parseVariableDeclarationStatement", "var x, y, z;", []);
+    VariableDeclarationStatement statement = ParserTestCase.parse("parseVariableDeclarationStatement", <Object> [emptyCommentAndMetadata()], "var x, y, z;");
     JUnitTestCase.assertNotNull(statement.semicolon);
     VariableDeclarationList variableList = statement.variables;
     JUnitTestCase.assertNotNull(variableList);
     EngineTestCase.assertSize(3, variableList.variables);
   }
   void test_parseVariableDeclarationStatement_single() {
-    VariableDeclarationStatement statement = ParserTestCase.parse6("parseVariableDeclarationStatement", "var x;", []);
+    VariableDeclarationStatement statement = ParserTestCase.parse("parseVariableDeclarationStatement", <Object> [emptyCommentAndMetadata()], "var x;");
     JUnitTestCase.assertNotNull(statement.semicolon);
     VariableDeclarationList variableList = statement.variables;
     JUnitTestCase.assertNotNull(variableList);
     EngineTestCase.assertSize(1, variableList.variables);
   }
   void test_parseWhileStatement() {
-    WhileStatement statement = ParserTestCase.parse6("parseWhileStatement", "while (x) {}", []);
+    WhileStatement statement = ParserTestCase.parse5("parseWhileStatement", "while (x) {}", []);
     JUnitTestCase.assertNotNull(statement.keyword);
     JUnitTestCase.assertNotNull(statement.leftParenthesis);
     JUnitTestCase.assertNotNull(statement.condition);
@@ -3416,12 +3432,12 @@
     JUnitTestCase.assertNotNull(statement.body);
   }
   void test_parseWithClause_multiple() {
-    WithClause clause = ParserTestCase.parse6("parseWithClause", "with A, B, C", []);
+    WithClause clause = ParserTestCase.parse5("parseWithClause", "with A, B, C", []);
     JUnitTestCase.assertNotNull(clause.withKeyword);
     EngineTestCase.assertSize(3, clause.mixinTypes);
   }
   void test_parseWithClause_single() {
-    WithClause clause = ParserTestCase.parse6("parseWithClause", "with M", []);
+    WithClause clause = ParserTestCase.parse5("parseWithClause", "with M", []);
     JUnitTestCase.assertNotNull(clause.withKeyword);
     EngineTestCase.assertSize(1, clause.mixinTypes);
   }
@@ -3521,7 +3537,7 @@
    * @throws Exception if the method could not be invoked or throws an exception
    */
   String computeStringValue(String lexeme) {
-    AnalysisErrorListener listener = new AnalysisErrorListener_13();
+    AnalysisErrorListener listener = new AnalysisErrorListener_15();
     Parser parser = new Parser(null, listener);
     return invokeParserMethodImpl(parser, "computeStringValue", <Object> [lexeme], null) as String;
   }
@@ -4416,22 +4432,6 @@
         final __test = new SimpleParserTest();
         runJUnitTest(__test, __test.test_parseContinueStatement_noLabel);
       });
-      _ut.test('test_parseDeclaredIdentifier_const', () {
-        final __test = new SimpleParserTest();
-        runJUnitTest(__test, __test.test_parseDeclaredIdentifier_const);
-      });
-      _ut.test('test_parseDeclaredIdentifier_final', () {
-        final __test = new SimpleParserTest();
-        runJUnitTest(__test, __test.test_parseDeclaredIdentifier_final);
-      });
-      _ut.test('test_parseDeclaredIdentifier_type', () {
-        final __test = new SimpleParserTest();
-        runJUnitTest(__test, __test.test_parseDeclaredIdentifier_type);
-      });
-      _ut.test('test_parseDeclaredIdentifier_var', () {
-        final __test = new SimpleParserTest();
-        runJUnitTest(__test, __test.test_parseDeclaredIdentifier_var);
-      });
       _ut.test('test_parseDirective_export', () {
         final __test = new SimpleParserTest();
         runJUnitTest(__test, __test.test_parseDirective_export);
@@ -4608,6 +4608,10 @@
         final __test = new SimpleParserTest();
         runJUnitTest(__test, __test.test_parseForStatement_loop_i);
       });
+      _ut.test('test_parseForStatement_loop_i_withMetadata', () {
+        final __test = new SimpleParserTest();
+        runJUnitTest(__test, __test.test_parseForStatement_loop_i_withMetadata);
+      });
       _ut.test('test_parseForStatement_loop_ic', () {
         final __test = new SimpleParserTest();
         runJUnitTest(__test, __test.test_parseForStatement_loop_ic);
@@ -5220,6 +5224,10 @@
         final __test = new SimpleParserTest();
         runJUnitTest(__test, __test.test_parseRelationalExpression_super);
       });
+      _ut.test('test_parseRethrowExpression', () {
+        final __test = new SimpleParserTest();
+        runJUnitTest(__test, __test.test_parseRethrowExpression);
+      });
       _ut.test('test_parseReturnStatement_noValue', () {
         final __test = new SimpleParserTest();
         runJUnitTest(__test, __test.test_parseReturnStatement_noValue);
@@ -5324,21 +5332,13 @@
         final __test = new SimpleParserTest();
         runJUnitTest(__test, __test.test_parseSwitchStatement_labeledStatementInCase);
       });
-      _ut.test('test_parseThrowExpressionWithoutCascade_expression', () {
+      _ut.test('test_parseThrowExpression', () {
         final __test = new SimpleParserTest();
-        runJUnitTest(__test, __test.test_parseThrowExpressionWithoutCascade_expression);
+        runJUnitTest(__test, __test.test_parseThrowExpression);
       });
-      _ut.test('test_parseThrowExpressionWithoutCascade_noExpression', () {
+      _ut.test('test_parseThrowExpressionWithoutCascade', () {
         final __test = new SimpleParserTest();
-        runJUnitTest(__test, __test.test_parseThrowExpressionWithoutCascade_noExpression);
-      });
-      _ut.test('test_parseThrowExpression_expression', () {
-        final __test = new SimpleParserTest();
-        runJUnitTest(__test, __test.test_parseThrowExpression_expression);
-      });
-      _ut.test('test_parseThrowExpression_noExpression', () {
-        final __test = new SimpleParserTest();
-        runJUnitTest(__test, __test.test_parseThrowExpression_noExpression);
+        runJUnitTest(__test, __test.test_parseThrowExpressionWithoutCascade);
       });
       _ut.test('test_parseTryStatement_catch', () {
         final __test = new SimpleParserTest();
@@ -5452,10 +5452,22 @@
         final __test = new SimpleParserTest();
         runJUnitTest(__test, __test.test_parseUnaryExpression_decrement_super);
       });
+      _ut.test('test_parseUnaryExpression_decrement_super_propertyAccess', () {
+        final __test = new SimpleParserTest();
+        runJUnitTest(__test, __test.test_parseUnaryExpression_decrement_super_propertyAccess);
+      });
       _ut.test('test_parseUnaryExpression_increment_normal', () {
         final __test = new SimpleParserTest();
         runJUnitTest(__test, __test.test_parseUnaryExpression_increment_normal);
       });
+      _ut.test('test_parseUnaryExpression_increment_super_index', () {
+        final __test = new SimpleParserTest();
+        runJUnitTest(__test, __test.test_parseUnaryExpression_increment_super_index);
+      });
+      _ut.test('test_parseUnaryExpression_increment_super_propertyAccess', () {
+        final __test = new SimpleParserTest();
+        runJUnitTest(__test, __test.test_parseUnaryExpression_increment_super_propertyAccess);
+      });
       _ut.test('test_parseUnaryExpression_minus_normal', () {
         final __test = new SimpleParserTest();
         runJUnitTest(__test, __test.test_parseUnaryExpression_minus_normal);
@@ -5627,7 +5639,7 @@
     });
   }
 }
-class AnalysisErrorListener_13 implements AnalysisErrorListener {
+class AnalysisErrorListener_15 implements AnalysisErrorListener {
   void onError(AnalysisError event) {
     JUnitTestCase.fail("Unexpected compilation error: ${event.message} (${event.offset}, ${event.length})");
   }
@@ -6072,13 +6084,13 @@
    * @param node the AST node being validated
    */
   void validate(ASTNode node) {
-    ASTNode parent20 = node.parent;
+    ASTNode parent22 = node.parent;
     if (node is CompilationUnit) {
-      if (parent20 != null) {
+      if (parent22 != null) {
         _errors.add("Compilation units should not have a parent");
       }
     } else {
-      if (parent20 == null) {
+      if (parent22 == null) {
         _errors.add("No parent for ${node.runtimeType.toString()}");
       }
     }
@@ -6093,15 +6105,15 @@
     if (nodeStart < 0 || nodeLength < 0) {
       _errors.add("No source info for ${node.runtimeType.toString()}");
     }
-    if (parent20 != null) {
+    if (parent22 != null) {
       int nodeEnd = nodeStart + nodeLength;
-      int parentStart = parent20.offset;
-      int parentEnd = parentStart + parent20.length;
+      int parentStart = parent22.offset;
+      int parentEnd = parentStart + parent22.length;
       if (nodeStart < parentStart) {
-        _errors.add("Invalid source start (${nodeStart}) for ${node.runtimeType.toString()} inside ${parent20.runtimeType.toString()} (${parentStart})");
+        _errors.add("Invalid source start (${nodeStart}) for ${node.runtimeType.toString()} inside ${parent22.runtimeType.toString()} (${parentStart})");
       }
       if (nodeEnd > parentEnd) {
-        _errors.add("Invalid source end (${nodeEnd}) for ${node.runtimeType.toString()} inside ${parent20.runtimeType.toString()} (${parentStart})");
+        _errors.add("Invalid source end (${nodeEnd}) for ${node.runtimeType.toString()} inside ${parent22.runtimeType.toString()} (${parentStart})");
       }
     }
   }
@@ -6124,7 +6136,7 @@
    * @throws Exception if the method could not be invoked or throws an exception
    * @throws AssertionFailedError if the result is {@code null} or if any errors are produced
    */
-  static Object parse(String methodName, List<Object> objects, String source) => parse4(methodName, objects, source, new List<AnalysisError>(0));
+  static Object parse(String methodName, List<Object> objects, String source) => parse3(methodName, objects, source, new List<AnalysisError>(0));
   /**
    * Invoke a parse method in {@link Parser}. The method is assumed to have the given number and
    * type of parameters and will be invoked with the given arguments.
@@ -6140,7 +6152,7 @@
    * @throws AssertionFailedError if the result is {@code null} or the errors produced while
    * scanning and parsing the source do not match the expected errors
    */
-  static Object parse4(String methodName, List<Object> objects, String source, List<AnalysisError> errors) {
+  static Object parse3(String methodName, List<Object> objects, String source, List<AnalysisError> errors) {
     GatheringErrorListener listener = new GatheringErrorListener();
     Object result = invokeParserMethod(methodName, objects, source, listener);
     listener.assertErrors(errors);
@@ -6161,7 +6173,7 @@
    * @throws AssertionFailedError if the result is {@code null} or the errors produced while
    * scanning and parsing the source do not match the expected errors
    */
-  static Object parse5(String methodName, List<Object> objects, String source, List<ErrorCode> errorCodes) {
+  static Object parse4(String methodName, List<Object> objects, String source, List<ErrorCode> errorCodes) {
     GatheringErrorListener listener = new GatheringErrorListener();
     Object result = invokeParserMethod(methodName, objects, source, listener);
     listener.assertErrors2(errorCodes);
@@ -6180,7 +6192,7 @@
    * @throws AssertionFailedError if the result is {@code null} or the errors produced while
    * scanning and parsing the source do not match the expected errors
    */
-  static Object parse6(String methodName, String source, List<ErrorCode> errorCodes) => parse5(methodName, _EMPTY_ARGUMENTS, source, errorCodes);
+  static Object parse5(String methodName, String source, List<ErrorCode> errorCodes) => parse4(methodName, _EMPTY_ARGUMENTS, source, errorCodes);
   /**
    * Parse the given source as a compilation unit.
    * @param source the source to be parsed
@@ -6494,12 +6506,12 @@
     EngineTestCase.assertInstanceOf(BinaryExpression, expression.leftOperand);
   }
   void test_conditionalExpression_missingElse() {
-    ConditionalExpression expression = ParserTestCase.parse6("parseConditionalExpression", "x ? y :", []);
+    ConditionalExpression expression = ParserTestCase.parse5("parseConditionalExpression", "x ? y :", []);
     EngineTestCase.assertInstanceOf(SimpleIdentifier, expression.elseExpression);
     JUnitTestCase.assertTrue(expression.elseExpression.isSynthetic());
   }
   void test_conditionalExpression_missingThen() {
-    ConditionalExpression expression = ParserTestCase.parse6("parseConditionalExpression", "x ? : z", []);
+    ConditionalExpression expression = ParserTestCase.parse5("parseConditionalExpression", "x ? : z", []);
     EngineTestCase.assertInstanceOf(SimpleIdentifier, expression.thenExpression);
     JUnitTestCase.assertTrue(expression.thenExpression.isSynthetic());
   }
@@ -6538,21 +6550,21 @@
     EngineTestCase.assertInstanceOf(BinaryExpression, expression.leftOperand);
   }
   void test_expressionList_multiple_end() {
-    List<Expression> result = ParserTestCase.parse6("parseExpressionList", ", 2, 3, 4", []);
+    List<Expression> result = ParserTestCase.parse5("parseExpressionList", ", 2, 3, 4", []);
     EngineTestCase.assertSize(4, result);
     Expression syntheticExpression = result[0];
     EngineTestCase.assertInstanceOf(SimpleIdentifier, syntheticExpression);
     JUnitTestCase.assertTrue(syntheticExpression.isSynthetic());
   }
   void test_expressionList_multiple_middle() {
-    List<Expression> result = ParserTestCase.parse6("parseExpressionList", "1, 2, , 4", []);
+    List<Expression> result = ParserTestCase.parse5("parseExpressionList", "1, 2, , 4", []);
     EngineTestCase.assertSize(4, result);
     Expression syntheticExpression = result[2];
     EngineTestCase.assertInstanceOf(SimpleIdentifier, syntheticExpression);
     JUnitTestCase.assertTrue(syntheticExpression.isSynthetic());
   }
   void test_expressionList_multiple_start() {
-    List<Expression> result = ParserTestCase.parse6("parseExpressionList", "1, 2, 3,", []);
+    List<Expression> result = ParserTestCase.parse5("parseExpressionList", "1, 2, 3,", []);
     EngineTestCase.assertSize(4, result);
     Expression syntheticExpression = result[3];
     EngineTestCase.assertInstanceOf(SimpleIdentifier, syntheticExpression);
@@ -7044,526 +7056,532 @@
  */
 class ErrorParserTest extends ParserTestCase {
   void fail_expectedListOrMapLiteral() {
-    TypedLiteral literal = ParserTestCase.parse5("parseListOrMapLiteral", <Object> [null], "1", [ParserErrorCode.EXPECTED_LIST_OR_MAP_LITERAL]);
+    TypedLiteral literal = ParserTestCase.parse4("parseListOrMapLiteral", <Object> [null], "1", [ParserErrorCode.EXPECTED_LIST_OR_MAP_LITERAL]);
     JUnitTestCase.assertTrue(literal.isSynthetic());
   }
   void fail_illegalAssignmentToNonAssignable_superAssigned() {
-    ParserTestCase.parse6("parseExpression", "super = x;", [ParserErrorCode.ILLEGAL_ASSIGNMENT_TO_NON_ASSIGNABLE]);
+    ParserTestCase.parse5("parseExpression", "super = x;", [ParserErrorCode.ILLEGAL_ASSIGNMENT_TO_NON_ASSIGNABLE]);
   }
   void fail_invalidCommentReference__new_nonIdentifier() {
-    ParserTestCase.parse5("parseCommentReference", <Object> ["new 42", 0], "", [ParserErrorCode.INVALID_COMMENT_REFERENCE]);
+    ParserTestCase.parse4("parseCommentReference", <Object> ["new 42", 0], "", [ParserErrorCode.INVALID_COMMENT_REFERENCE]);
   }
   void fail_invalidCommentReference__new_tooMuch() {
-    ParserTestCase.parse5("parseCommentReference", <Object> ["new a.b.c.d", 0], "", [ParserErrorCode.INVALID_COMMENT_REFERENCE]);
+    ParserTestCase.parse4("parseCommentReference", <Object> ["new a.b.c.d", 0], "", [ParserErrorCode.INVALID_COMMENT_REFERENCE]);
   }
   void fail_invalidCommentReference__nonNew_nonIdentifier() {
-    ParserTestCase.parse5("parseCommentReference", <Object> ["42", 0], "", [ParserErrorCode.INVALID_COMMENT_REFERENCE]);
+    ParserTestCase.parse4("parseCommentReference", <Object> ["42", 0], "", [ParserErrorCode.INVALID_COMMENT_REFERENCE]);
   }
   void fail_invalidCommentReference__nonNew_tooMuch() {
-    ParserTestCase.parse5("parseCommentReference", <Object> ["a.b.c.d", 0], "", [ParserErrorCode.INVALID_COMMENT_REFERENCE]);
+    ParserTestCase.parse4("parseCommentReference", <Object> ["a.b.c.d", 0], "", [ParserErrorCode.INVALID_COMMENT_REFERENCE]);
+  }
+  void fail_missingExpressionInThrow_withCascade() {
+    ParserTestCase.parse5("parseThrowExpression", "throw;", [ParserErrorCode.MISSING_EXPRESSION_IN_THROW]);
+  }
+  void fail_missingExpressionInThrow_withoutCascade() {
+    ParserTestCase.parse5("parseThrowExpressionWithoutCascade", "throw;", [ParserErrorCode.MISSING_EXPRESSION_IN_THROW]);
   }
   void fail_missingFunctionParameters_local_nonVoid_block() {
-    ParserTestCase.parse6("parseStatement", "int f { return x;}", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
+    ParserTestCase.parse5("parseStatement", "int f { return x;}", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
   }
   void fail_missingFunctionParameters_local_nonVoid_expression() {
-    ParserTestCase.parse6("parseStatement", "int f => x;", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
+    ParserTestCase.parse5("parseStatement", "int f => x;", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
   }
   void fail_unexpectedToken_invalidPostfixExpression() {
-    ParserTestCase.parse6("parseExpression", "f()++", [ParserErrorCode.UNEXPECTED_TOKEN]);
+    ParserTestCase.parse5("parseExpression", "f()++", [ParserErrorCode.UNEXPECTED_TOKEN]);
   }
   void fail_voidVariable_initializer() {
-    ParserTestCase.parse6("parseStatement", "void x = 0;", [ParserErrorCode.VOID_VARIABLE]);
+    ParserTestCase.parse5("parseStatement", "void x = 0;", [ParserErrorCode.VOID_VARIABLE]);
   }
   void fail_voidVariable_noInitializer() {
-    ParserTestCase.parse6("parseStatement", "void x;", [ParserErrorCode.VOID_VARIABLE]);
+    ParserTestCase.parse5("parseStatement", "void x;", [ParserErrorCode.VOID_VARIABLE]);
   }
   void test_abstractClassMember_constructor() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "abstract C.c();", [ParserErrorCode.ABSTRACT_CLASS_MEMBER]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "abstract C.c();", [ParserErrorCode.ABSTRACT_CLASS_MEMBER]);
   }
   void test_abstractClassMember_field() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "abstract C f;", [ParserErrorCode.ABSTRACT_CLASS_MEMBER]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "abstract C f;", [ParserErrorCode.ABSTRACT_CLASS_MEMBER]);
   }
   void test_abstractClassMember_getter() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "abstract get m;", [ParserErrorCode.ABSTRACT_CLASS_MEMBER]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "abstract get m;", [ParserErrorCode.ABSTRACT_CLASS_MEMBER]);
   }
   void test_abstractClassMember_method() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "abstract m();", [ParserErrorCode.ABSTRACT_CLASS_MEMBER]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "abstract m();", [ParserErrorCode.ABSTRACT_CLASS_MEMBER]);
   }
   void test_abstractClassMember_setter() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "abstract set m(v);", [ParserErrorCode.ABSTRACT_CLASS_MEMBER]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "abstract set m(v);", [ParserErrorCode.ABSTRACT_CLASS_MEMBER]);
   }
   void test_abstractTopLevelFunction_function() {
-    ParserTestCase.parse6("parseCompilationUnit", "abstract f(v) {}", [ParserErrorCode.ABSTRACT_TOP_LEVEL_FUNCTION]);
+    ParserTestCase.parse5("parseCompilationUnit", "abstract f(v) {}", [ParserErrorCode.ABSTRACT_TOP_LEVEL_FUNCTION]);
   }
   void test_abstractTopLevelFunction_getter() {
-    ParserTestCase.parse6("parseCompilationUnit", "abstract get m {}", [ParserErrorCode.ABSTRACT_TOP_LEVEL_FUNCTION]);
+    ParserTestCase.parse5("parseCompilationUnit", "abstract get m {}", [ParserErrorCode.ABSTRACT_TOP_LEVEL_FUNCTION]);
   }
   void test_abstractTopLevelFunction_setter() {
-    ParserTestCase.parse6("parseCompilationUnit", "abstract set m(v) {}", [ParserErrorCode.ABSTRACT_TOP_LEVEL_FUNCTION]);
+    ParserTestCase.parse5("parseCompilationUnit", "abstract set m(v) {}", [ParserErrorCode.ABSTRACT_TOP_LEVEL_FUNCTION]);
   }
   void test_abstractTopLevelVariable() {
-    ParserTestCase.parse6("parseCompilationUnit", "abstract C f;", [ParserErrorCode.ABSTRACT_TOP_LEVEL_VARIABLE]);
+    ParserTestCase.parse5("parseCompilationUnit", "abstract C f;", [ParserErrorCode.ABSTRACT_TOP_LEVEL_VARIABLE]);
   }
   void test_abstractTypeDef() {
-    ParserTestCase.parse6("parseCompilationUnit", "abstract typedef F();", [ParserErrorCode.ABSTRACT_TYPEDEF]);
+    ParserTestCase.parse5("parseCompilationUnit", "abstract typedef F();", [ParserErrorCode.ABSTRACT_TYPEDEF]);
   }
   void test_breakOutsideOfLoop_breakInDoStatement() {
-    ParserTestCase.parse6("parseDoStatement", "do {break;} while (x);", []);
+    ParserTestCase.parse5("parseDoStatement", "do {break;} while (x);", []);
   }
   void test_breakOutsideOfLoop_breakInForStatement() {
-    ParserTestCase.parse6("parseForStatement", "for (; x;) {break;}", []);
+    ParserTestCase.parse5("parseForStatement", "for (; x;) {break;}", []);
   }
   void test_breakOutsideOfLoop_breakInIfStatement() {
-    ParserTestCase.parse6("parseIfStatement", "if (x) {break;}", [ParserErrorCode.BREAK_OUTSIDE_OF_LOOP]);
+    ParserTestCase.parse5("parseIfStatement", "if (x) {break;}", [ParserErrorCode.BREAK_OUTSIDE_OF_LOOP]);
   }
   void test_breakOutsideOfLoop_breakInSwitchStatement() {
-    ParserTestCase.parse6("parseSwitchStatement", "switch (x) {case 1: break;}", []);
+    ParserTestCase.parse5("parseSwitchStatement", "switch (x) {case 1: break;}", []);
   }
   void test_breakOutsideOfLoop_breakInWhileStatement() {
-    ParserTestCase.parse6("parseWhileStatement", "while (x) {break;}", []);
+    ParserTestCase.parse5("parseWhileStatement", "while (x) {break;}", []);
   }
   void test_breakOutsideOfLoop_functionExpression_inALoop() {
-    ParserTestCase.parse6("parseStatement", "for(; x;) {() {break;};}", [ParserErrorCode.BREAK_OUTSIDE_OF_LOOP]);
+    ParserTestCase.parse5("parseStatement", "for(; x;) {() {break;};}", [ParserErrorCode.BREAK_OUTSIDE_OF_LOOP]);
   }
   void test_breakOutsideOfLoop_functionExpression_withALoop() {
-    ParserTestCase.parse6("parseStatement", "() {for (; x;) {break;}};", []);
+    ParserTestCase.parse5("parseStatement", "() {for (; x;) {break;}};", []);
   }
   void test_constAndFinal() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "const final int x;", [ParserErrorCode.CONST_AND_FINAL]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "const final int x;", [ParserErrorCode.CONST_AND_FINAL]);
   }
   void test_constAndVar() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "const var x;", [ParserErrorCode.CONST_AND_VAR]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "const var x;", [ParserErrorCode.CONST_AND_VAR]);
   }
   void test_constClass() {
-    ParserTestCase.parse6("parseCompilationUnit", "const class C {}", [ParserErrorCode.CONST_CLASS]);
+    ParserTestCase.parse5("parseCompilationUnit", "const class C {}", [ParserErrorCode.CONST_CLASS]);
   }
   void test_constMethod() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "const int m() {}", [ParserErrorCode.CONST_METHOD]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "const int m() {}", [ParserErrorCode.CONST_METHOD]);
   }
   void test_constTypedef() {
-    ParserTestCase.parse6("parseCompilationUnit", "const typedef F();", [ParserErrorCode.CONST_TYPEDEF]);
+    ParserTestCase.parse5("parseCompilationUnit", "const typedef F();", [ParserErrorCode.CONST_TYPEDEF]);
   }
   void test_continueOutsideOfLoop_continueInDoStatement() {
-    ParserTestCase.parse6("parseDoStatement", "do {continue;} while (x);", []);
+    ParserTestCase.parse5("parseDoStatement", "do {continue;} while (x);", []);
   }
   void test_continueOutsideOfLoop_continueInForStatement() {
-    ParserTestCase.parse6("parseForStatement", "for (; x;) {continue;}", []);
+    ParserTestCase.parse5("parseForStatement", "for (; x;) {continue;}", []);
   }
   void test_continueOutsideOfLoop_continueInIfStatement() {
-    ParserTestCase.parse6("parseIfStatement", "if (x) {continue;}", [ParserErrorCode.CONTINUE_OUTSIDE_OF_LOOP]);
+    ParserTestCase.parse5("parseIfStatement", "if (x) {continue;}", [ParserErrorCode.CONTINUE_OUTSIDE_OF_LOOP]);
   }
   void test_continueOutsideOfLoop_continueInSwitchStatement() {
-    ParserTestCase.parse6("parseSwitchStatement", "switch (x) {case 1: continue a;}", []);
+    ParserTestCase.parse5("parseSwitchStatement", "switch (x) {case 1: continue a;}", []);
   }
   void test_continueOutsideOfLoop_continueInWhileStatement() {
-    ParserTestCase.parse6("parseWhileStatement", "while (x) {continue;}", []);
+    ParserTestCase.parse5("parseWhileStatement", "while (x) {continue;}", []);
   }
   void test_continueOutsideOfLoop_functionExpression_inALoop() {
-    ParserTestCase.parse6("parseStatement", "for(; x;) {() {continue;};}", [ParserErrorCode.CONTINUE_OUTSIDE_OF_LOOP]);
+    ParserTestCase.parse5("parseStatement", "for(; x;) {() {continue;};}", [ParserErrorCode.CONTINUE_OUTSIDE_OF_LOOP]);
   }
   void test_continueOutsideOfLoop_functionExpression_withALoop() {
-    ParserTestCase.parse6("parseStatement", "() {for (; x;) {continue;}};", []);
+    ParserTestCase.parse5("parseStatement", "() {for (; x;) {continue;}};", []);
   }
   void test_continueWithoutLabelInCase_error() {
-    ParserTestCase.parse6("parseSwitchStatement", "switch (x) {case 1: continue;}", [ParserErrorCode.CONTINUE_WITHOUT_LABEL_IN_CASE]);
+    ParserTestCase.parse5("parseSwitchStatement", "switch (x) {case 1: continue;}", [ParserErrorCode.CONTINUE_WITHOUT_LABEL_IN_CASE]);
   }
   void test_continueWithoutLabelInCase_noError() {
-    ParserTestCase.parse6("parseSwitchStatement", "switch (x) {case 1: continue a;}", []);
+    ParserTestCase.parse5("parseSwitchStatement", "switch (x) {case 1: continue a;}", []);
   }
   void test_continueWithoutLabelInCase_noError_switchInLoop() {
-    ParserTestCase.parse6("parseWhileStatement", "while (a) { switch (b) {default: continue;}}", []);
+    ParserTestCase.parse5("parseWhileStatement", "while (a) { switch (b) {default: continue;}}", []);
   }
   void test_directiveAfterDeclaration_classBeforeDirective() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "class Foo{} library l;", [ParserErrorCode.DIRECTIVE_AFTER_DECLARATION]);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "class Foo{} library l;", [ParserErrorCode.DIRECTIVE_AFTER_DECLARATION]);
     JUnitTestCase.assertNotNull(unit);
   }
   void test_directiveAfterDeclaration_classBetweenDirectives() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "library l;\nclass Foo{}\npart 'a.dart';", [ParserErrorCode.DIRECTIVE_AFTER_DECLARATION]);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "library l;\nclass Foo{}\npart 'a.dart';", [ParserErrorCode.DIRECTIVE_AFTER_DECLARATION]);
     JUnitTestCase.assertNotNull(unit);
   }
   void test_duplicatedModifier_const() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "const const m;", [ParserErrorCode.DUPLICATED_MODIFIER]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "const const m;", [ParserErrorCode.DUPLICATED_MODIFIER]);
   }
   void test_duplicatedModifier_external() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external external f();", [ParserErrorCode.DUPLICATED_MODIFIER]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external external f();", [ParserErrorCode.DUPLICATED_MODIFIER]);
   }
   void test_duplicatedModifier_factory() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "factory factory C() {}", [ParserErrorCode.DUPLICATED_MODIFIER]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "factory factory C() {}", [ParserErrorCode.DUPLICATED_MODIFIER]);
   }
   void test_duplicatedModifier_final() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "final final m;", [ParserErrorCode.DUPLICATED_MODIFIER]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "final final m;", [ParserErrorCode.DUPLICATED_MODIFIER]);
   }
   void test_duplicatedModifier_static() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "static static m;", [ParserErrorCode.DUPLICATED_MODIFIER]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "static static m;", [ParserErrorCode.DUPLICATED_MODIFIER]);
   }
   void test_duplicatedModifier_var() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "var var m;", [ParserErrorCode.DUPLICATED_MODIFIER]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "var var m;", [ParserErrorCode.DUPLICATED_MODIFIER]);
   }
   void test_duplicateLabelInSwitchStatement() {
-    ParserTestCase.parse6("parseSwitchStatement", "switch (e) {l1: case 0: break; l1: case 1: break;}", [ParserErrorCode.DUPLICATE_LABEL_IN_SWITCH_STATEMENT]);
+    ParserTestCase.parse5("parseSwitchStatement", "switch (e) {l1: case 0: break; l1: case 1: break;}", [ParserErrorCode.DUPLICATE_LABEL_IN_SWITCH_STATEMENT]);
   }
   void test_expectedCaseOrDefault() {
-    ParserTestCase.parse6("parseSwitchStatement", "switch (e) {break;}", [ParserErrorCode.EXPECTED_CASE_OR_DEFAULT]);
+    ParserTestCase.parse5("parseSwitchStatement", "switch (e) {break;}", [ParserErrorCode.EXPECTED_CASE_OR_DEFAULT]);
   }
   void test_expectedStringLiteral() {
-    StringLiteral expression = ParserTestCase.parse6("parseStringLiteral", "1", [ParserErrorCode.EXPECTED_STRING_LITERAL]);
+    StringLiteral expression = ParserTestCase.parse5("parseStringLiteral", "1", [ParserErrorCode.EXPECTED_STRING_LITERAL]);
     JUnitTestCase.assertTrue(expression.isSynthetic());
   }
   void test_expectedToken_commaMissingInArgumentList() {
-    ParserTestCase.parse6("parseArgumentList", "(x, y z)", [ParserErrorCode.EXPECTED_TOKEN]);
+    ParserTestCase.parse5("parseArgumentList", "(x, y z)", [ParserErrorCode.EXPECTED_TOKEN]);
   }
   void test_expectedToken_semicolonMissingAfterExpression() {
-    ParserTestCase.parse6("parseStatement", "x", [ParserErrorCode.EXPECTED_TOKEN]);
+    ParserTestCase.parse5("parseStatement", "x", [ParserErrorCode.EXPECTED_TOKEN]);
   }
   void test_expectedToken_whileMissingInDoStatement() {
-    ParserTestCase.parse6("parseStatement", "do {} (x);", [ParserErrorCode.EXPECTED_TOKEN]);
+    ParserTestCase.parse5("parseStatement", "do {} (x);", [ParserErrorCode.EXPECTED_TOKEN]);
   }
   void test_exportDirectiveAfterPartDirective() {
-    ParserTestCase.parse6("parseCompilationUnit", "part 'a.dart'; export 'b.dart';", [ParserErrorCode.EXPORT_DIRECTIVE_AFTER_PART_DIRECTIVE]);
+    ParserTestCase.parse5("parseCompilationUnit", "part 'a.dart'; export 'b.dart';", [ParserErrorCode.EXPORT_DIRECTIVE_AFTER_PART_DIRECTIVE]);
   }
   void test_externalAfterConst() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "const external C();", [ParserErrorCode.EXTERNAL_AFTER_CONST]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "const external C();", [ParserErrorCode.EXTERNAL_AFTER_CONST]);
   }
   void test_externalAfterFactory() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "factory external C();", [ParserErrorCode.EXTERNAL_AFTER_FACTORY]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "factory external C();", [ParserErrorCode.EXTERNAL_AFTER_FACTORY]);
   }
   void test_externalAfterStatic() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "static external int m();", [ParserErrorCode.EXTERNAL_AFTER_STATIC]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "static external int m();", [ParserErrorCode.EXTERNAL_AFTER_STATIC]);
   }
   void test_externalClass() {
-    ParserTestCase.parse6("parseCompilationUnit", "external class C {}", [ParserErrorCode.EXTERNAL_CLASS]);
+    ParserTestCase.parse5("parseCompilationUnit", "external class C {}", [ParserErrorCode.EXTERNAL_CLASS]);
   }
   void test_externalConstructorWithBody_factory() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external factory C() {}", [ParserErrorCode.EXTERNAL_CONSTRUCTOR_WITH_BODY]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external factory C() {}", [ParserErrorCode.EXTERNAL_CONSTRUCTOR_WITH_BODY]);
   }
   void test_externalConstructorWithBody_named() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external C.c() {}", [ParserErrorCode.EXTERNAL_CONSTRUCTOR_WITH_BODY]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external C.c() {}", [ParserErrorCode.EXTERNAL_CONSTRUCTOR_WITH_BODY]);
   }
   void test_externalField_const() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external const A f;", [ParserErrorCode.EXTERNAL_FIELD]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external const A f;", [ParserErrorCode.EXTERNAL_FIELD]);
   }
   void test_externalField_final() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external final A f;", [ParserErrorCode.EXTERNAL_FIELD]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external final A f;", [ParserErrorCode.EXTERNAL_FIELD]);
   }
   void test_externalField_static() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external static A f;", [ParserErrorCode.EXTERNAL_FIELD]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external static A f;", [ParserErrorCode.EXTERNAL_FIELD]);
   }
   void test_externalField_typed() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external A f;", [ParserErrorCode.EXTERNAL_FIELD]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external A f;", [ParserErrorCode.EXTERNAL_FIELD]);
   }
   void test_externalField_untyped() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external var f;", [ParserErrorCode.EXTERNAL_FIELD]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external var f;", [ParserErrorCode.EXTERNAL_FIELD]);
   }
   void test_externalGetterWithBody() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external int get x {}", [ParserErrorCode.EXTERNAL_GETTER_WITH_BODY]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external int get x {}", [ParserErrorCode.EXTERNAL_GETTER_WITH_BODY]);
   }
   void test_externalMethodWithBody() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external m() {}", [ParserErrorCode.EXTERNAL_METHOD_WITH_BODY]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external m() {}", [ParserErrorCode.EXTERNAL_METHOD_WITH_BODY]);
   }
   void test_externalOperatorWithBody() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external operator +(int value) {}", [ParserErrorCode.EXTERNAL_OPERATOR_WITH_BODY]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external operator +(int value) {}", [ParserErrorCode.EXTERNAL_OPERATOR_WITH_BODY]);
   }
   void test_externalSetterWithBody() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "external set x(int value) {}", [ParserErrorCode.EXTERNAL_SETTER_WITH_BODY]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "external set x(int value) {}", [ParserErrorCode.EXTERNAL_SETTER_WITH_BODY]);
   }
   void test_externalTypedef() {
-    ParserTestCase.parse6("parseCompilationUnit", "external typedef F();", [ParserErrorCode.EXTERNAL_TYPEDEF]);
+    ParserTestCase.parse5("parseCompilationUnit", "external typedef F();", [ParserErrorCode.EXTERNAL_TYPEDEF]);
   }
   void test_factoryTopLevelDeclaration_class() {
-    ParserTestCase.parse6("parseCompilationUnit", "factory class C {}", [ParserErrorCode.FACTORY_TOP_LEVEL_DECLARATION]);
+    ParserTestCase.parse5("parseCompilationUnit", "factory class C {}", [ParserErrorCode.FACTORY_TOP_LEVEL_DECLARATION]);
   }
   void test_factoryTopLevelDeclaration_typedef() {
-    ParserTestCase.parse6("parseCompilationUnit", "factory typedef F();", [ParserErrorCode.FACTORY_TOP_LEVEL_DECLARATION]);
+    ParserTestCase.parse5("parseCompilationUnit", "factory typedef F();", [ParserErrorCode.FACTORY_TOP_LEVEL_DECLARATION]);
   }
   void test_fieldInitializerOutsideConstructor() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "void m(this.x);", [ParserErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "void m(this.x);", [ParserErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR]);
   }
   void test_finalAndVar() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "final var x;", [ParserErrorCode.FINAL_AND_VAR]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "final var x;", [ParserErrorCode.FINAL_AND_VAR]);
   }
   void test_finalClass() {
-    ParserTestCase.parse6("parseCompilationUnit", "final class C {}", [ParserErrorCode.FINAL_CLASS]);
+    ParserTestCase.parse5("parseCompilationUnit", "final class C {}", [ParserErrorCode.FINAL_CLASS]);
   }
   void test_finalConstructor() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "final C() {}", [ParserErrorCode.FINAL_CONSTRUCTOR]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "final C() {}", [ParserErrorCode.FINAL_CONSTRUCTOR]);
   }
   void test_finalMethod() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "final int m() {}", [ParserErrorCode.FINAL_METHOD]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "final int m() {}", [ParserErrorCode.FINAL_METHOD]);
   }
   void test_finalTypedef() {
-    ParserTestCase.parse6("parseCompilationUnit", "final typedef F();", [ParserErrorCode.FINAL_TYPEDEF]);
+    ParserTestCase.parse5("parseCompilationUnit", "final typedef F();", [ParserErrorCode.FINAL_TYPEDEF]);
   }
   void test_getterWithParameters() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "int get x() {}", [ParserErrorCode.GETTER_WITH_PARAMETERS]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "int get x() {}", [ParserErrorCode.GETTER_WITH_PARAMETERS]);
   }
   void test_illegalAssignmentToNonAssignable_superAssigned() {
-    ParserTestCase.parse6("parseExpression", "super = x;", [ParserErrorCode.MISSING_ASSIGNABLE_SELECTOR, ParserErrorCode.ILLEGAL_ASSIGNMENT_TO_NON_ASSIGNABLE]);
+    ParserTestCase.parse5("parseExpression", "super = x;", [ParserErrorCode.MISSING_ASSIGNABLE_SELECTOR, ParserErrorCode.ILLEGAL_ASSIGNMENT_TO_NON_ASSIGNABLE]);
   }
   void test_implementsBeforeExtends() {
-    ParserTestCase.parse6("parseCompilationUnit", "class A implements B extends C {}", [ParserErrorCode.IMPLEMENTS_BEFORE_EXTENDS]);
+    ParserTestCase.parse5("parseCompilationUnit", "class A implements B extends C {}", [ParserErrorCode.IMPLEMENTS_BEFORE_EXTENDS]);
   }
   void test_implementsBeforeWith() {
-    ParserTestCase.parse6("parseCompilationUnit", "class A extends B implements C with D {}", [ParserErrorCode.IMPLEMENTS_BEFORE_WITH]);
+    ParserTestCase.parse5("parseCompilationUnit", "class A extends B implements C with D {}", [ParserErrorCode.IMPLEMENTS_BEFORE_WITH]);
   }
   void test_importDirectiveAfterPartDirective() {
-    ParserTestCase.parse6("parseCompilationUnit", "part 'a.dart'; import 'b.dart';", [ParserErrorCode.IMPORT_DIRECTIVE_AFTER_PART_DIRECTIVE]);
+    ParserTestCase.parse5("parseCompilationUnit", "part 'a.dart'; import 'b.dart';", [ParserErrorCode.IMPORT_DIRECTIVE_AFTER_PART_DIRECTIVE]);
   }
   void test_initializedVariableInForEach() {
-    ParserTestCase.parse6("parseForStatement", "for (int a = 0 in foo) {}", [ParserErrorCode.INITIALIZED_VARIABLE_IN_FOR_EACH]);
+    ParserTestCase.parse5("parseForStatement", "for (int a = 0 in foo) {}", [ParserErrorCode.INITIALIZED_VARIABLE_IN_FOR_EACH]);
   }
   void test_invalidCodePoint() {
-    ParserTestCase.parse6("parseStringLiteral", "'\\uD900'", [ParserErrorCode.INVALID_CODE_POINT]);
+    ParserTestCase.parse5("parseStringLiteral", "'\\uD900'", [ParserErrorCode.INVALID_CODE_POINT]);
   }
   void test_invalidHexEscape_invalidDigit() {
-    ParserTestCase.parse6("parseStringLiteral", "'\\x0 a'", [ParserErrorCode.INVALID_HEX_ESCAPE]);
+    ParserTestCase.parse5("parseStringLiteral", "'\\x0 a'", [ParserErrorCode.INVALID_HEX_ESCAPE]);
   }
   void test_invalidHexEscape_tooFewDigits() {
-    ParserTestCase.parse6("parseStringLiteral", "'\\x0'", [ParserErrorCode.INVALID_HEX_ESCAPE]);
+    ParserTestCase.parse5("parseStringLiteral", "'\\x0'", [ParserErrorCode.INVALID_HEX_ESCAPE]);
   }
   void test_invalidOperatorForSuper() {
-    ParserTestCase.parse6("parseUnaryExpression", "++super", [ParserErrorCode.INVALID_OPERATOR_FOR_SUPER]);
+    ParserTestCase.parse5("parseUnaryExpression", "++super", [ParserErrorCode.INVALID_OPERATOR_FOR_SUPER]);
   }
   void test_invalidUnicodeEscape_incomplete_noDigits() {
-    ParserTestCase.parse6("parseStringLiteral", "'\\u{'", [ParserErrorCode.INVALID_UNICODE_ESCAPE]);
+    ParserTestCase.parse5("parseStringLiteral", "'\\u{'", [ParserErrorCode.INVALID_UNICODE_ESCAPE]);
   }
   void test_invalidUnicodeEscape_incomplete_someDigits() {
-    ParserTestCase.parse6("parseStringLiteral", "'\\u{0A'", [ParserErrorCode.INVALID_UNICODE_ESCAPE]);
+    ParserTestCase.parse5("parseStringLiteral", "'\\u{0A'", [ParserErrorCode.INVALID_UNICODE_ESCAPE]);
   }
   void test_invalidUnicodeEscape_invalidDigit() {
-    ParserTestCase.parse6("parseStringLiteral", "'\\u0 a'", [ParserErrorCode.INVALID_UNICODE_ESCAPE]);
+    ParserTestCase.parse5("parseStringLiteral", "'\\u0 a'", [ParserErrorCode.INVALID_UNICODE_ESCAPE]);
   }
   void test_invalidUnicodeEscape_tooFewDigits_fixed() {
-    ParserTestCase.parse6("parseStringLiteral", "'\\u04'", [ParserErrorCode.INVALID_UNICODE_ESCAPE]);
+    ParserTestCase.parse5("parseStringLiteral", "'\\u04'", [ParserErrorCode.INVALID_UNICODE_ESCAPE]);
   }
   void test_invalidUnicodeEscape_tooFewDigits_variable() {
-    ParserTestCase.parse6("parseStringLiteral", "'\\u{}'", [ParserErrorCode.INVALID_UNICODE_ESCAPE]);
+    ParserTestCase.parse5("parseStringLiteral", "'\\u{}'", [ParserErrorCode.INVALID_UNICODE_ESCAPE]);
   }
   void test_invalidUnicodeEscape_tooManyDigits_variable() {
-    ParserTestCase.parse6("parseStringLiteral", "'\\u{12345678}'", [ParserErrorCode.INVALID_UNICODE_ESCAPE, ParserErrorCode.INVALID_CODE_POINT]);
+    ParserTestCase.parse5("parseStringLiteral", "'\\u{12345678}'", [ParserErrorCode.INVALID_UNICODE_ESCAPE, ParserErrorCode.INVALID_CODE_POINT]);
   }
   void test_libraryDirectiveNotFirst() {
-    ParserTestCase.parse6("parseCompilationUnit", "import 'x.dart'; library l;", [ParserErrorCode.LIBRARY_DIRECTIVE_NOT_FIRST]);
+    ParserTestCase.parse5("parseCompilationUnit", "import 'x.dart'; library l;", [ParserErrorCode.LIBRARY_DIRECTIVE_NOT_FIRST]);
   }
   void test_libraryDirectiveNotFirst_afterPart() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "part 'a.dart';\nlibrary l;", [ParserErrorCode.LIBRARY_DIRECTIVE_NOT_FIRST]);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "part 'a.dart';\nlibrary l;", [ParserErrorCode.LIBRARY_DIRECTIVE_NOT_FIRST]);
     JUnitTestCase.assertNotNull(unit);
   }
   void test_missingAssignableSelector_identifiersAssigned() {
-    ParserTestCase.parse6("parseExpression", "x.y = y;", []);
+    ParserTestCase.parse5("parseExpression", "x.y = y;", []);
   }
   void test_missingAssignableSelector_primarySelectorPostfix() {
-    ParserTestCase.parse6("parseExpression", "x(y)(z)++", [ParserErrorCode.MISSING_ASSIGNABLE_SELECTOR]);
+    ParserTestCase.parse5("parseExpression", "x(y)(z)++", [ParserErrorCode.MISSING_ASSIGNABLE_SELECTOR]);
   }
   void test_missingAssignableSelector_selector() {
-    ParserTestCase.parse6("parseExpression", "x(y)(z).a++", []);
+    ParserTestCase.parse5("parseExpression", "x(y)(z).a++", []);
   }
   void test_missingAssignableSelector_superPrimaryExpression() {
-    SuperExpression expression = ParserTestCase.parse6("parsePrimaryExpression", "super", [ParserErrorCode.MISSING_ASSIGNABLE_SELECTOR]);
+    SuperExpression expression = ParserTestCase.parse5("parsePrimaryExpression", "super", [ParserErrorCode.MISSING_ASSIGNABLE_SELECTOR]);
     JUnitTestCase.assertNotNull(expression.keyword);
   }
   void test_missingAssignableSelector_superPropertyAccessAssigned() {
-    ParserTestCase.parse6("parseExpression", "super.x = x;", []);
+    ParserTestCase.parse5("parseExpression", "super.x = x;", []);
   }
   void test_missingCatchOrFinally() {
-    TryStatement statement = ParserTestCase.parse6("parseTryStatement", "try {}", [ParserErrorCode.MISSING_CATCH_OR_FINALLY]);
+    TryStatement statement = ParserTestCase.parse5("parseTryStatement", "try {}", [ParserErrorCode.MISSING_CATCH_OR_FINALLY]);
     JUnitTestCase.assertNotNull(statement);
   }
   void test_missingClassBody() {
-    ParserTestCase.parse6("parseCompilationUnit", "class A class B {}", [ParserErrorCode.MISSING_CLASS_BODY]);
+    ParserTestCase.parse5("parseCompilationUnit", "class A class B {}", [ParserErrorCode.MISSING_CLASS_BODY]);
   }
   void test_missingConstFinalVarOrType() {
-    ParserTestCase.parse5("parseFinalConstVarOrType", <Object> [false], "a;", [ParserErrorCode.MISSING_CONST_FINAL_VAR_OR_TYPE]);
+    ParserTestCase.parse4("parseFinalConstVarOrType", <Object> [false], "a;", [ParserErrorCode.MISSING_CONST_FINAL_VAR_OR_TYPE]);
   }
   void test_missingFunctionBody_emptyNotAllowed() {
-    ParserTestCase.parse5("parseFunctionBody", <Object> [false, false], ";", [ParserErrorCode.MISSING_FUNCTION_BODY]);
+    ParserTestCase.parse4("parseFunctionBody", <Object> [false, false], ";", [ParserErrorCode.MISSING_FUNCTION_BODY]);
   }
   void test_missingFunctionBody_invalid() {
-    ParserTestCase.parse5("parseFunctionBody", <Object> [false, false], "return 0;", [ParserErrorCode.MISSING_FUNCTION_BODY]);
+    ParserTestCase.parse4("parseFunctionBody", <Object> [false, false], "return 0;", [ParserErrorCode.MISSING_FUNCTION_BODY]);
   }
   void test_missingFunctionParameters_local_void_block() {
-    ParserTestCase.parse6("parseStatement", "void f { return x;}", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
+    ParserTestCase.parse5("parseStatement", "void f { return x;}", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
   }
   void test_missingFunctionParameters_local_void_expression() {
-    ParserTestCase.parse6("parseStatement", "void f => x;", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
+    ParserTestCase.parse5("parseStatement", "void f => x;", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
   }
   void test_missingFunctionParameters_topLevel_nonVoid_block() {
-    ParserTestCase.parse6("parseCompilationUnit", "int f { return x;}", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
+    ParserTestCase.parse5("parseCompilationUnit", "int f { return x;}", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
   }
   void test_missingFunctionParameters_topLevel_nonVoid_expression() {
-    ParserTestCase.parse6("parseCompilationUnit", "int f => x;", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
+    ParserTestCase.parse5("parseCompilationUnit", "int f => x;", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
   }
   void test_missingFunctionParameters_topLevel_void_block() {
-    ParserTestCase.parse6("parseCompilationUnit", "void f { return x;}", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
+    ParserTestCase.parse5("parseCompilationUnit", "void f { return x;}", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
   }
   void test_missingFunctionParameters_topLevel_void_expression() {
-    ParserTestCase.parse6("parseCompilationUnit", "void f => x;", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
+    ParserTestCase.parse5("parseCompilationUnit", "void f => x;", [ParserErrorCode.MISSING_FUNCTION_PARAMETERS]);
   }
   void test_missingIdentifier_functionDeclaration_returnTypeWithoutName() {
-    ParserTestCase.parse6("parseFunctionDeclarationStatement", "A<T> () {}", [ParserErrorCode.MISSING_IDENTIFIER]);
+    ParserTestCase.parse5("parseFunctionDeclarationStatement", "A<T> () {}", [ParserErrorCode.MISSING_IDENTIFIER]);
   }
   void test_missingIdentifier_number() {
-    SimpleIdentifier expression = ParserTestCase.parse6("parseSimpleIdentifier", "1", [ParserErrorCode.MISSING_IDENTIFIER]);
+    SimpleIdentifier expression = ParserTestCase.parse5("parseSimpleIdentifier", "1", [ParserErrorCode.MISSING_IDENTIFIER]);
     JUnitTestCase.assertTrue(expression.isSynthetic());
   }
   void test_missingNameInLibraryDirective() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "library;", [ParserErrorCode.MISSING_NAME_IN_LIBRARY_DIRECTIVE]);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "library;", [ParserErrorCode.MISSING_NAME_IN_LIBRARY_DIRECTIVE]);
     JUnitTestCase.assertNotNull(unit);
   }
   void test_missingNameInPartOfDirective() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "part of;", [ParserErrorCode.MISSING_NAME_IN_PART_OF_DIRECTIVE]);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "part of;", [ParserErrorCode.MISSING_NAME_IN_PART_OF_DIRECTIVE]);
     JUnitTestCase.assertNotNull(unit);
   }
   void test_missingTerminatorForParameterGroup_named() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, {b: 0)", [ParserErrorCode.MISSING_TERMINATOR_FOR_PARAMETER_GROUP]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, {b: 0)", [ParserErrorCode.MISSING_TERMINATOR_FOR_PARAMETER_GROUP]);
   }
   void test_missingTerminatorForParameterGroup_optional() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, [b = 0)", [ParserErrorCode.MISSING_TERMINATOR_FOR_PARAMETER_GROUP]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, [b = 0)", [ParserErrorCode.MISSING_TERMINATOR_FOR_PARAMETER_GROUP]);
   }
   void test_missingTypedefParameters_nonVoid() {
-    ParserTestCase.parse6("parseCompilationUnit", "typedef int F;", [ParserErrorCode.MISSING_TYPEDEF_PARAMETERS]);
+    ParserTestCase.parse5("parseCompilationUnit", "typedef int F;", [ParserErrorCode.MISSING_TYPEDEF_PARAMETERS]);
   }
   void test_missingTypedefParameters_typeParameters() {
-    ParserTestCase.parse6("parseCompilationUnit", "typedef F<E>;", [ParserErrorCode.MISSING_TYPEDEF_PARAMETERS]);
+    ParserTestCase.parse5("parseCompilationUnit", "typedef F<E>;", [ParserErrorCode.MISSING_TYPEDEF_PARAMETERS]);
   }
   void test_missingTypedefParameters_void() {
-    ParserTestCase.parse6("parseCompilationUnit", "typedef void F;", [ParserErrorCode.MISSING_TYPEDEF_PARAMETERS]);
+    ParserTestCase.parse5("parseCompilationUnit", "typedef void F;", [ParserErrorCode.MISSING_TYPEDEF_PARAMETERS]);
   }
   void test_missingVariableInForEach() {
-    ParserTestCase.parse6("parseForStatement", "for (a < b in foo) {}", [ParserErrorCode.MISSING_VARIABLE_IN_FOR_EACH]);
+    ParserTestCase.parse5("parseForStatement", "for (a < b in foo) {}", [ParserErrorCode.MISSING_VARIABLE_IN_FOR_EACH]);
   }
   void test_mixedParameterGroups_namedPositional() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, {b}, [c])", [ParserErrorCode.MIXED_PARAMETER_GROUPS]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, {b}, [c])", [ParserErrorCode.MIXED_PARAMETER_GROUPS]);
   }
   void test_mixedParameterGroups_positionalNamed() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, [b], {c})", [ParserErrorCode.MIXED_PARAMETER_GROUPS]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, [b], {c})", [ParserErrorCode.MIXED_PARAMETER_GROUPS]);
   }
   void test_multipleLibraryDirectives() {
-    ParserTestCase.parse6("parseCompilationUnit", "library l; library m;", [ParserErrorCode.MULTIPLE_LIBRARY_DIRECTIVES]);
+    ParserTestCase.parse5("parseCompilationUnit", "library l; library m;", [ParserErrorCode.MULTIPLE_LIBRARY_DIRECTIVES]);
   }
   void test_multipleNamedParameterGroups() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, {b}, {c})", [ParserErrorCode.MULTIPLE_NAMED_PARAMETER_GROUPS]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, {b}, {c})", [ParserErrorCode.MULTIPLE_NAMED_PARAMETER_GROUPS]);
   }
   void test_multiplePartOfDirectives() {
-    ParserTestCase.parse6("parseCompilationUnit", "part of l; part of m;", [ParserErrorCode.MULTIPLE_PART_OF_DIRECTIVES]);
+    ParserTestCase.parse5("parseCompilationUnit", "part of l; part of m;", [ParserErrorCode.MULTIPLE_PART_OF_DIRECTIVES]);
   }
   void test_multiplePositionalParameterGroups() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, [b], [c])", [ParserErrorCode.MULTIPLE_POSITIONAL_PARAMETER_GROUPS]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, [b], [c])", [ParserErrorCode.MULTIPLE_POSITIONAL_PARAMETER_GROUPS]);
   }
   void test_multipleVariablesInForEach() {
-    ParserTestCase.parse6("parseForStatement", "for (int a, b in foo) {}", [ParserErrorCode.MULTIPLE_VARIABLES_IN_FOR_EACH]);
+    ParserTestCase.parse5("parseForStatement", "for (int a, b in foo) {}", [ParserErrorCode.MULTIPLE_VARIABLES_IN_FOR_EACH]);
   }
   void test_namedParameterOutsideGroup() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, b : 0)", [ParserErrorCode.NAMED_PARAMETER_OUTSIDE_GROUP]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, b : 0)", [ParserErrorCode.NAMED_PARAMETER_OUTSIDE_GROUP]);
   }
   void test_nonConstructorFactory_field() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "factory int x;", [ParserErrorCode.NON_CONSTRUCTOR_FACTORY]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "factory int x;", [ParserErrorCode.NON_CONSTRUCTOR_FACTORY]);
   }
   void test_nonConstructorFactory_method() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "factory int m() {}", [ParserErrorCode.NON_CONSTRUCTOR_FACTORY]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "factory int m() {}", [ParserErrorCode.NON_CONSTRUCTOR_FACTORY]);
   }
   void test_nonIdentifierLibraryName_library() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "library 'lib';", [ParserErrorCode.NON_IDENTIFIER_LIBRARY_NAME]);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "library 'lib';", [ParserErrorCode.NON_IDENTIFIER_LIBRARY_NAME]);
     JUnitTestCase.assertNotNull(unit);
   }
   void test_nonIdentifierLibraryName_partOf() {
-    CompilationUnit unit = ParserTestCase.parse6("parseCompilationUnit", "part of 'lib';", [ParserErrorCode.NON_IDENTIFIER_LIBRARY_NAME]);
+    CompilationUnit unit = ParserTestCase.parse5("parseCompilationUnit", "part of 'lib';", [ParserErrorCode.NON_IDENTIFIER_LIBRARY_NAME]);
     JUnitTestCase.assertNotNull(unit);
   }
   void test_nonPartOfDirectiveInPart_after() {
-    ParserTestCase.parse6("parseCompilationUnit", "part of l; part 'f.dart';", [ParserErrorCode.NON_PART_OF_DIRECTIVE_IN_PART]);
+    ParserTestCase.parse5("parseCompilationUnit", "part of l; part 'f.dart';", [ParserErrorCode.NON_PART_OF_DIRECTIVE_IN_PART]);
   }
   void test_nonPartOfDirectiveInPart_before() {
-    ParserTestCase.parse6("parseCompilationUnit", "part 'f.dart'; part of m;", [ParserErrorCode.NON_PART_OF_DIRECTIVE_IN_PART]);
+    ParserTestCase.parse5("parseCompilationUnit", "part 'f.dart'; part of m;", [ParserErrorCode.NON_PART_OF_DIRECTIVE_IN_PART]);
   }
   void test_nonUserDefinableOperator() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "operator +=(int x) => x + 1;", [ParserErrorCode.NON_USER_DEFINABLE_OPERATOR]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "operator +=(int x) => x + 1;", [ParserErrorCode.NON_USER_DEFINABLE_OPERATOR]);
   }
   void test_positionalAfterNamedArgument() {
-    ParserTestCase.parse6("parseArgumentList", "(x: 1, 2)", [ParserErrorCode.POSITIONAL_AFTER_NAMED_ARGUMENT]);
+    ParserTestCase.parse5("parseArgumentList", "(x: 1, 2)", [ParserErrorCode.POSITIONAL_AFTER_NAMED_ARGUMENT]);
   }
   void test_positionalParameterOutsideGroup() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, b = 0)", [ParserErrorCode.POSITIONAL_PARAMETER_OUTSIDE_GROUP]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, b = 0)", [ParserErrorCode.POSITIONAL_PARAMETER_OUTSIDE_GROUP]);
   }
   void test_staticAfterConst() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "final static int f;", [ParserErrorCode.STATIC_AFTER_FINAL]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "final static int f;", [ParserErrorCode.STATIC_AFTER_FINAL]);
   }
   void test_staticAfterFinal() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "const static int f;", [ParserErrorCode.STATIC_AFTER_CONST]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "const static int f;", [ParserErrorCode.STATIC_AFTER_CONST]);
   }
   void test_staticAfterVar() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "var static f;", [ParserErrorCode.STATIC_AFTER_VAR]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "var static f;", [ParserErrorCode.STATIC_AFTER_VAR]);
   }
   void test_staticConstructor() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "static C.m() {}", [ParserErrorCode.STATIC_CONSTRUCTOR]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "static C.m() {}", [ParserErrorCode.STATIC_CONSTRUCTOR]);
   }
   void test_staticOperator_noReturnType() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "static operator +(int x) => x + 1;", [ParserErrorCode.STATIC_OPERATOR]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "static operator +(int x) => x + 1;", [ParserErrorCode.STATIC_OPERATOR]);
   }
   void test_staticOperator_returnType() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "static int operator +(int x) => x + 1;", [ParserErrorCode.STATIC_OPERATOR]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "static int operator +(int x) => x + 1;", [ParserErrorCode.STATIC_OPERATOR]);
   }
   void test_staticTopLevelDeclaration_class() {
-    ParserTestCase.parse6("parseCompilationUnit", "static class C {}", [ParserErrorCode.STATIC_TOP_LEVEL_DECLARATION]);
+    ParserTestCase.parse5("parseCompilationUnit", "static class C {}", [ParserErrorCode.STATIC_TOP_LEVEL_DECLARATION]);
   }
   void test_staticTopLevelDeclaration_typedef() {
-    ParserTestCase.parse6("parseCompilationUnit", "static typedef F();", [ParserErrorCode.STATIC_TOP_LEVEL_DECLARATION]);
+    ParserTestCase.parse5("parseCompilationUnit", "static typedef F();", [ParserErrorCode.STATIC_TOP_LEVEL_DECLARATION]);
   }
   void test_staticTopLevelDeclaration_variable() {
-    ParserTestCase.parse6("parseCompilationUnit", "static var x;", [ParserErrorCode.STATIC_TOP_LEVEL_DECLARATION]);
+    ParserTestCase.parse5("parseCompilationUnit", "static var x;", [ParserErrorCode.STATIC_TOP_LEVEL_DECLARATION]);
   }
   void test_unexpectedTerminatorForParameterGroup_named() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, b})", [ParserErrorCode.UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, b})", [ParserErrorCode.UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP]);
   }
   void test_unexpectedTerminatorForParameterGroup_optional() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, b])", [ParserErrorCode.UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, b])", [ParserErrorCode.UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP]);
   }
   void test_unexpectedToken_semicolonBetweenClassMembers() {
-    ParserTestCase.parse5("parseClassDeclaration", <Object> [emptyCommentAndMetadata(), null], "class C { int x; ; int y;}", [ParserErrorCode.UNEXPECTED_TOKEN]);
+    ParserTestCase.parse4("parseClassDeclaration", <Object> [emptyCommentAndMetadata(), null], "class C { int x; ; int y;}", [ParserErrorCode.UNEXPECTED_TOKEN]);
   }
   void test_unexpectedToken_semicolonBetweenCompilationUnitMembers() {
-    ParserTestCase.parse6("parseCompilationUnit", "int x; ; int y;", [ParserErrorCode.UNEXPECTED_TOKEN]);
+    ParserTestCase.parse5("parseCompilationUnit", "int x; ; int y;", [ParserErrorCode.UNEXPECTED_TOKEN]);
   }
   void test_useOfUnaryPlusOperator() {
-    ParserTestCase.parse6("parseUnaryExpression", "+x", [ParserErrorCode.USE_OF_UNARY_PLUS_OPERATOR]);
+    ParserTestCase.parse5("parseUnaryExpression", "+x", [ParserErrorCode.USE_OF_UNARY_PLUS_OPERATOR]);
   }
   void test_varClass() {
-    ParserTestCase.parse6("parseCompilationUnit", "var class C {}", [ParserErrorCode.VAR_CLASS]);
+    ParserTestCase.parse5("parseCompilationUnit", "var class C {}", [ParserErrorCode.VAR_CLASS]);
   }
   void test_varConstructor() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "var C() {}", [ParserErrorCode.CONSTRUCTOR_WITH_RETURN_TYPE]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "var C() {}", [ParserErrorCode.CONSTRUCTOR_WITH_RETURN_TYPE]);
   }
   void test_varReturnType() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "var m() {}", [ParserErrorCode.VAR_RETURN_TYPE]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "var m() {}", [ParserErrorCode.VAR_RETURN_TYPE]);
   }
   void test_varTypedef() {
-    ParserTestCase.parse6("parseCompilationUnit", "var typedef F();", [ParserErrorCode.VAR_TYPEDEF]);
+    ParserTestCase.parse5("parseCompilationUnit", "var typedef F();", [ParserErrorCode.VAR_TYPEDEF]);
   }
   void test_voidField_initializer() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "void x = 0;", [ParserErrorCode.VOID_VARIABLE]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "void x = 0;", [ParserErrorCode.VOID_VARIABLE]);
   }
   void test_voidField_noInitializer() {
-    ParserTestCase.parse5("parseClassMember", <Object> ["C"], "void x;", [ParserErrorCode.VOID_VARIABLE]);
+    ParserTestCase.parse4("parseClassMember", <Object> ["C"], "void x;", [ParserErrorCode.VOID_VARIABLE]);
   }
   void test_voidParameter() {
-    ParserTestCase.parse6("parseNormalFormalParameter", "void a)", [ParserErrorCode.VOID_PARAMETER]);
+    ParserTestCase.parse5("parseNormalFormalParameter", "void a)", [ParserErrorCode.VOID_PARAMETER]);
   }
   void test_withBeforeExtends() {
-    ParserTestCase.parse6("parseCompilationUnit", "class A with B extends C {}", [ParserErrorCode.WITH_BEFORE_EXTENDS]);
+    ParserTestCase.parse5("parseCompilationUnit", "class A with B extends C {}", [ParserErrorCode.WITH_BEFORE_EXTENDS]);
   }
   void test_withWithoutExtends() {
-    ParserTestCase.parse5("parseClassDeclaration", <Object> [emptyCommentAndMetadata(), null], "class A with B, C {}", [ParserErrorCode.WITH_WITHOUT_EXTENDS]);
+    ParserTestCase.parse4("parseClassDeclaration", <Object> [emptyCommentAndMetadata(), null], "class A with B, C {}", [ParserErrorCode.WITH_WITHOUT_EXTENDS]);
   }
   void test_wrongSeparatorForNamedParameter() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, {b = 0})", [ParserErrorCode.WRONG_SEPARATOR_FOR_NAMED_PARAMETER]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, {b = 0})", [ParserErrorCode.WRONG_SEPARATOR_FOR_NAMED_PARAMETER]);
   }
   void test_wrongSeparatorForPositionalParameter() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, [b : 0])", [ParserErrorCode.WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, [b : 0])", [ParserErrorCode.WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER]);
   }
   void test_wrongTerminatorForParameterGroup_named() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, {b, c])", [ParserErrorCode.WRONG_TERMINATOR_FOR_PARAMETER_GROUP]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, {b, c])", [ParserErrorCode.WRONG_TERMINATOR_FOR_PARAMETER_GROUP]);
   }
   void test_wrongTerminatorForParameterGroup_optional() {
-    ParserTestCase.parse6("parseFormalParameterList", "(a, [b, c})", [ParserErrorCode.WRONG_TERMINATOR_FOR_PARAMETER_GROUP]);
+    ParserTestCase.parse5("parseFormalParameterList", "(a, [b, c})", [ParserErrorCode.WRONG_TERMINATOR_FOR_PARAMETER_GROUP]);
   }
   static dartSuite() {
     _ut.group('ErrorParserTest', () {
@@ -8268,7 +8286,6 @@
   'parseConstructorFieldInitializer_0': new MethodTrampoline(0, (Parser target) => target.parseConstructorFieldInitializer()),
   'parseConstructorName_0': new MethodTrampoline(0, (Parser target) => target.parseConstructorName()),
   'parseContinueStatement_0': new MethodTrampoline(0, (Parser target) => target.parseContinueStatement()),
-  'parseDeclaredIdentifier_1': new MethodTrampoline(1, (Parser target, arg0) => target.parseDeclaredIdentifier(arg0)),
   'parseDirective_1': new MethodTrampoline(1, (Parser target, arg0) => target.parseDirective(arg0)),
   'parseDocumentationComment_0': new MethodTrampoline(0, (Parser target) => target.parseDocumentationComment()),
   'parseDoStatement_0': new MethodTrampoline(0, (Parser target) => target.parseDoStatement()),
@@ -8320,6 +8337,7 @@
   'parsePrimaryExpression_0': new MethodTrampoline(0, (Parser target) => target.parsePrimaryExpression()),
   'parseRedirectingConstructorInvocation_0': new MethodTrampoline(0, (Parser target) => target.parseRedirectingConstructorInvocation()),
   'parseRelationalExpression_0': new MethodTrampoline(0, (Parser target) => target.parseRelationalExpression()),
+  'parseRethrowExpression_0': new MethodTrampoline(0, (Parser target) => target.parseRethrowExpression()),
   'parseReturnStatement_0': new MethodTrampoline(0, (Parser target) => target.parseReturnStatement()),
   'parseReturnType_0': new MethodTrampoline(0, (Parser target) => target.parseReturnType()),
   'parseSetter_4': new MethodTrampoline(4, (Parser target, arg0, arg1, arg2, arg3) => target.parseSetter(arg0, arg1, arg2, arg3)),
@@ -8341,9 +8359,9 @@
   'parseTypeParameterList_0': new MethodTrampoline(0, (Parser target) => target.parseTypeParameterList()),
   'parseUnaryExpression_0': new MethodTrampoline(0, (Parser target) => target.parseUnaryExpression()),
   'parseVariableDeclaration_0': new MethodTrampoline(0, (Parser target) => target.parseVariableDeclaration()),
-  'parseVariableDeclarationList_0': new MethodTrampoline(0, (Parser target) => target.parseVariableDeclarationList()),
-  'parseVariableDeclarationList_2': new MethodTrampoline(2, (Parser target, arg0, arg1) => target.parseVariableDeclarationList2(arg0, arg1)),
-  'parseVariableDeclarationStatement_0': new MethodTrampoline(0, (Parser target) => target.parseVariableDeclarationStatement()),
+  'parseVariableDeclarationList_1': new MethodTrampoline(1, (Parser target, arg0) => target.parseVariableDeclarationList(arg0)),
+  'parseVariableDeclarationList_3': new MethodTrampoline(3, (Parser target, arg0, arg1, arg2) => target.parseVariableDeclarationList2(arg0, arg1, arg2)),
+  'parseVariableDeclarationStatement_1': new MethodTrampoline(1, (Parser target, arg0) => target.parseVariableDeclarationStatement(arg0)),
   'parseWhileStatement_0': new MethodTrampoline(0, (Parser target) => target.parseWhileStatement()),
   'parseWithClause_0': new MethodTrampoline(0, (Parser target) => target.parseWithClause()),
   'peek_0': new MethodTrampoline(0, (Parser target) => target.peek()),
diff --git a/pkg/analyzer_experimental/test/generated/resolver_test.dart b/pkg/analyzer_experimental/test/generated/resolver_test.dart
index 963a3e9..da96c97 100644
--- a/pkg/analyzer_experimental/test/generated/resolver_test.dart
+++ b/pkg/analyzer_experimental/test/generated/resolver_test.dart
@@ -21,6 +21,322 @@
 import 'ast_test.dart' show ASTFactory;
 import 'element_test.dart' show ElementFactory;
 
+class NonErrorResolverTest extends ResolverTestCase {
+  void test_argumentDefinitionTestNonParameter_formalParameter() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["f(var v) {", "  return ?v;", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_argumentDefinitionTestNonParameter_namedParameter() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["f({var v : 0}) {", "  return ?v;", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_argumentDefinitionTestNonParameter_optionalParameter() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["f([var v]) {", "  return ?v;", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_breakWithoutLabelInSwitch() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  void m(int i) {", "    switch (i) {", "      case 0:", "        break;", "    }", "  }", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_builtInIdentifierAsType_dynamic() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  dynamic x;", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_caseExpressionTypeImplementsEquals_int() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["f(int i) {", "  switch(i) {", "    case(1) : return 1;", "    default: return 0;", "  }", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_caseExpressionTypeImplementsEquals_Object() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class IntWrapper {", "  final int value;", "  const IntWrapper(this.value);", "}", "", "f(IntWrapper intWrapper) {", "  switch(intWrapper) {", "    case(const IntWrapper(1)) : return 1;", "    default: return 0;", "  }", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_caseExpressionTypeImplementsEquals_String() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["f(String s) {", "  switch(s) {", "    case('1') : return 1;", "    default: return 0;", "  }", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_constConstructorWithNonFinalField_const() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  const int x;", "  const A() {}", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_constConstructorWithNonFinalField_final() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  final int x;", "  const A() {}", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_constConstructorWithNonFinalField_syntheticField() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  const A();", "  set x(value) {}", "  get x {return 0;}", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_defaultValueInFunctionTypeAlias() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["typedef F([x]);"]));
+    resolve(source, []);
+    assertErrors([]);
+    verify([source]);
+  }
+  void test_duplicateDefinition_getter() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["bool get a => true;"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_fieldInitializedInInitializerAndDeclaration_fieldNotFinal() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  int x = 0;", "  A() : x = 1 {}", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_fieldInitializedInInitializerAndDeclaration_finalFieldNotSet() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  final int x;", "  A() : x = 1 {}", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_fieldInitializerOutsideConstructor() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  int x;", "  A(this.x) {}", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_fieldInitializerOutsideConstructor_defaultParameters() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  int x;", "  A([this.x]) {}", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_invalidAssignment() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  var x;", "  var y;", "  x = y;", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_invalidAssignment_toDynamic() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  var g;", "  g = () => 0;", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_invocationOfNonFunction_dynamic() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  var f;", "}", "class B extends A {", "  g() {", "    f();", "  }", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_invocationOfNonFunction_getter() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  var g;", "}", "f() {", "  A a;", "  a.g();", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_invocationOfNonFunction_localVariable() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  var g;", "  g();", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_newWithAbstractClass_factory() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["abstract class A {", "  factory A() { return new B(); }", "}", "class B implements A {", "  B() {}", "}", "A f() {", "  return new A();", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_nonBoolExpression_assert_bool() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  assert(true);", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_nonBoolExpression_assert_functionType() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["bool makeAssertion() => true;", "f() {", "  assert(makeAssertion);", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_rethrowOutsideCatch() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  void m() {", "    try {} catch (e) {rethrow;}", "  }", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_returnOfInvalidType_dynamic() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  static void testLogicalOp() {", "    testOr(a, b, onTypeError) {", "      try {", "        return a || b;", "      } on TypeError catch (t) {", "        return onTypeError;", "      }", "    }", "  }", "}"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_returnOfInvalidType_subtype() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {}", "class B extends A {}", "A f(B b) { return b; }"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_returnOfInvalidType_supertype() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {}", "class B extends A {}", "B f(A a) { return a; }"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_typeArgumentNotMatchingBounds_const() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {}", "class B extends A {}", "class G<E extends A> {", "  const G() {}", "}", "f() { return const G<B>(); }"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  void test_typeArgumentNotMatchingBounds_new() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {}", "class B extends A {}", "class G<E extends A> {}", "f() { return new G<B>(); }"]));
+    resolve(source, []);
+    assertNoErrors();
+    verify([source]);
+  }
+  static dartSuite() {
+    _ut.group('NonErrorResolverTest', () {
+      _ut.test('test_argumentDefinitionTestNonParameter_formalParameter', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_argumentDefinitionTestNonParameter_formalParameter);
+      });
+      _ut.test('test_argumentDefinitionTestNonParameter_namedParameter', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_argumentDefinitionTestNonParameter_namedParameter);
+      });
+      _ut.test('test_argumentDefinitionTestNonParameter_optionalParameter', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_argumentDefinitionTestNonParameter_optionalParameter);
+      });
+      _ut.test('test_breakWithoutLabelInSwitch', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_breakWithoutLabelInSwitch);
+      });
+      _ut.test('test_builtInIdentifierAsType_dynamic', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_builtInIdentifierAsType_dynamic);
+      });
+      _ut.test('test_caseExpressionTypeImplementsEquals_Object', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_caseExpressionTypeImplementsEquals_Object);
+      });
+      _ut.test('test_caseExpressionTypeImplementsEquals_String', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_caseExpressionTypeImplementsEquals_String);
+      });
+      _ut.test('test_caseExpressionTypeImplementsEquals_int', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_caseExpressionTypeImplementsEquals_int);
+      });
+      _ut.test('test_constConstructorWithNonFinalField_const', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_constConstructorWithNonFinalField_const);
+      });
+      _ut.test('test_constConstructorWithNonFinalField_final', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_constConstructorWithNonFinalField_final);
+      });
+      _ut.test('test_constConstructorWithNonFinalField_syntheticField', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_constConstructorWithNonFinalField_syntheticField);
+      });
+      _ut.test('test_defaultValueInFunctionTypeAlias', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_defaultValueInFunctionTypeAlias);
+      });
+      _ut.test('test_duplicateDefinition_getter', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_duplicateDefinition_getter);
+      });
+      _ut.test('test_fieldInitializedInInitializerAndDeclaration_fieldNotFinal', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_fieldInitializedInInitializerAndDeclaration_fieldNotFinal);
+      });
+      _ut.test('test_fieldInitializedInInitializerAndDeclaration_finalFieldNotSet', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_fieldInitializedInInitializerAndDeclaration_finalFieldNotSet);
+      });
+      _ut.test('test_fieldInitializerOutsideConstructor', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_fieldInitializerOutsideConstructor);
+      });
+      _ut.test('test_fieldInitializerOutsideConstructor_defaultParameters', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_fieldInitializerOutsideConstructor_defaultParameters);
+      });
+      _ut.test('test_invalidAssignment', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_invalidAssignment);
+      });
+      _ut.test('test_invalidAssignment_toDynamic', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_invalidAssignment_toDynamic);
+      });
+      _ut.test('test_invocationOfNonFunction_dynamic', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_invocationOfNonFunction_dynamic);
+      });
+      _ut.test('test_invocationOfNonFunction_getter', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_invocationOfNonFunction_getter);
+      });
+      _ut.test('test_invocationOfNonFunction_localVariable', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_invocationOfNonFunction_localVariable);
+      });
+      _ut.test('test_newWithAbstractClass_factory', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_newWithAbstractClass_factory);
+      });
+      _ut.test('test_nonBoolExpression_assert_bool', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_nonBoolExpression_assert_bool);
+      });
+      _ut.test('test_nonBoolExpression_assert_functionType', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_nonBoolExpression_assert_functionType);
+      });
+      _ut.test('test_rethrowOutsideCatch', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_rethrowOutsideCatch);
+      });
+      _ut.test('test_returnOfInvalidType_dynamic', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_returnOfInvalidType_dynamic);
+      });
+      _ut.test('test_returnOfInvalidType_subtype', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_returnOfInvalidType_subtype);
+      });
+      _ut.test('test_returnOfInvalidType_supertype', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_returnOfInvalidType_supertype);
+      });
+      _ut.test('test_typeArgumentNotMatchingBounds_const', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_typeArgumentNotMatchingBounds_const);
+      });
+      _ut.test('test_typeArgumentNotMatchingBounds_new', () {
+        final __test = new NonErrorResolverTest();
+        runJUnitTest(__test, __test.test_typeArgumentNotMatchingBounds_new);
+      });
+    });
+  }
+}
 class LibraryTest extends EngineTestCase {
   /**
    * The error listener to which all errors will be reported.
@@ -753,6 +1069,9 @@
   Source addSource(String filePath, String contents) {
     Source source = new FileBasedSource.con1(_sourceFactory, FileUtilities2.createFile(filePath));
     _sourceFactory.setContents(source, contents);
+    ChangeSet changeSet = new ChangeSet();
+    changeSet.added(source);
+    _analysisContext.applyChanges(changeSet);
     return source;
   }
   /**
@@ -782,13 +1101,13 @@
       ClassElementImpl type = new ClassElementImpl(ASTFactory.identifier2(typeName));
       String fileName = "${typeName}.dart";
       CompilationUnitElementImpl compilationUnit = new CompilationUnitElementImpl(fileName);
-      compilationUnit.source = new FileBasedSource.con1(_sourceFactory, FileUtilities2.createFile(fileName));
+      compilationUnit.source = createSource2(fileName);
       compilationUnit.types = <ClassElement> [type];
       sourcedCompilationUnits[i] = compilationUnit;
     }
     String fileName = "${libraryName}.dart";
     CompilationUnitElementImpl compilationUnit = new CompilationUnitElementImpl(fileName);
-    compilationUnit.source = new FileBasedSource.con1(_sourceFactory, FileUtilities2.createFile(fileName));
+    compilationUnit.source = createSource2(fileName);
     LibraryElementImpl library = new LibraryElementImpl(context, ASTFactory.libraryIdentifier2([libraryName]));
     library.definingCompilationUnit = compilationUnit;
     library.parts = sourcedCompilationUnits;
@@ -821,10 +1140,20 @@
   void verify(List<Source> sources) {
     ResolutionVerifier verifier = new ResolutionVerifier();
     for (Source source in sources) {
-      _analysisContext.parse3(source, _errorListener).accept(verifier);
+      _analysisContext.parseCompilationUnit(source).accept(verifier);
     }
     verifier.assertResolved();
   }
+  /**
+   * Create a source object representing a file with the given name and give it an empty content.
+   * @param fileName the name of the file for which a source is to be created
+   * @return the source that was created
+   */
+  FileBasedSource createSource2(String fileName) {
+    FileBasedSource source = new FileBasedSource.con1(_sourceFactory, FileUtilities2.createFile(fileName));
+    _sourceFactory.setContents(source, "");
+    return source;
+  }
   static dartSuite() {
     _ut.group('ResolverTestCase', () {
     });
@@ -994,24 +1323,6 @@
     assertErrors([CompileTimeErrorCode.FIELD_INITIALIZED_BY_MULTIPLE_INITIALIZERS]);
     verify([source]);
   }
-  void fail_fieldInitializedInInitializerAndDeclaration() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  final int x = 0;", "  A() : x = 1 {}", "}"]));
-    resolve(source, []);
-    assertErrors([CompileTimeErrorCode.FIELD_INITIALIZED_IN_INITIALIZER_AND_DECLARATION]);
-    verify([source]);
-  }
-  void fail_fieldInitializeInParameterAndInitializer() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  int x;", "  A(this.x) : x = 1 {}", "}"]));
-    resolve(source, []);
-    assertErrors([CompileTimeErrorCode.FIELD_INITIALIZED_IN_PARAMETER_AND_INITIALIZER]);
-    verify([source]);
-  }
-  void fail_fieldInitializerOutsideConstructor() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  int x;", "  m(this.x) {}", "}"]));
-    resolve(source, []);
-    assertErrors([CompileTimeErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR]);
-    verify([source]);
-  }
   void fail_finalInitializedInDeclarationAndConstructor_assignment() {
     Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  final x = 0;", "  A() { x = 1; }", "}"]));
     resolve(source, []);
@@ -1424,12 +1735,6 @@
     assertErrors([CompileTimeErrorCode.SUPER_INITIALIZER_IN_OBJECT]);
     verify([source]);
   }
-  void fail_throwWithoutValueOutsideOn() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  throw;", "}"]));
-    resolve(source, []);
-    assertErrors([CompileTimeErrorCode.THROW_WITHOUT_VALUE_OUTSIDE_ON]);
-    verify([source]);
-  }
   void fail_typeArgumentsForNonGenericClass_creation_const() {
     Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {}", "f(p) {", "  return const A<int>();", "}"]));
     resolve(source, []);
@@ -1696,6 +2001,36 @@
     assertErrors([CompileTimeErrorCode.IMPLEMENTS_DISALLOWED_CLASS]);
     verify([source]);
   }
+  void test_fieldInitializedInInitializerAndDeclaration_const() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  const int x = 0;", "  A() : x = 1 {}", "}"]));
+    resolve(source, []);
+    assertErrors([CompileTimeErrorCode.FIELD_INITIALIZED_IN_INITIALIZER_AND_DECLARATION]);
+    verify([source]);
+  }
+  void test_fieldInitializedInInitializerAndDeclaration_final() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  final int x = 0;", "  A() : x = 1 {}", "}"]));
+    resolve(source, []);
+    assertErrors([CompileTimeErrorCode.FIELD_INITIALIZED_IN_INITIALIZER_AND_DECLARATION]);
+    verify([source]);
+  }
+  void test_fieldInitializeInParameterAndInitializer() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  int x;", "  A(this.x) : x = 1 {}", "}"]));
+    resolve(source, []);
+    assertErrors([CompileTimeErrorCode.FIELD_INITIALIZED_IN_PARAMETER_AND_INITIALIZER]);
+    verify([source]);
+  }
+  void test_fieldInitializerOutsideConstructor() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  int x;", "  m(this.x) {}", "}"]));
+    resolve(source, []);
+    assertErrors([CompileTimeErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR]);
+    verify([source]);
+  }
+  void test_fieldInitializerOutsideConstructor_defaultParameters() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  int x;", "  m([this.x]) {}", "}"]));
+    resolve(source, []);
+    assertErrors([CompileTimeErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR]);
+    verify([source]);
+  }
   void test_implementsNonClass() {
     Source source = addSource("/test.dart", EngineTestCase.createSource(["int A;", "class B implements A {}"]));
     resolve(source, []);
@@ -1741,6 +2076,12 @@
     assertErrors([CompileTimeErrorCode.NON_CONSTANT_MAP_VALUE]);
     verify([source]);
   }
+  void test_rethrowOutsideCatch() {
+    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  rethrow;", "}"]));
+    resolve(source, []);
+    assertErrors([CompileTimeErrorCode.RETHROW_OUTSIDE_CATCH]);
+    verify([source]);
+  }
   void test_uriWithInterpolation_constant() {
     Source source = addSource("/test.dart", EngineTestCase.createSource(["import 'stuff_\$platform.dart';"]));
     resolve(source, []);
@@ -1873,6 +2214,26 @@
         final __test = new CompileTimeErrorCodeTest();
         runJUnitTest(__test, __test.test_extendsOrImplementsDisallowedClass_implements_num);
       });
+      _ut.test('test_fieldInitializeInParameterAndInitializer', () {
+        final __test = new CompileTimeErrorCodeTest();
+        runJUnitTest(__test, __test.test_fieldInitializeInParameterAndInitializer);
+      });
+      _ut.test('test_fieldInitializedInInitializerAndDeclaration_const', () {
+        final __test = new CompileTimeErrorCodeTest();
+        runJUnitTest(__test, __test.test_fieldInitializedInInitializerAndDeclaration_const);
+      });
+      _ut.test('test_fieldInitializedInInitializerAndDeclaration_final', () {
+        final __test = new CompileTimeErrorCodeTest();
+        runJUnitTest(__test, __test.test_fieldInitializedInInitializerAndDeclaration_final);
+      });
+      _ut.test('test_fieldInitializerOutsideConstructor', () {
+        final __test = new CompileTimeErrorCodeTest();
+        runJUnitTest(__test, __test.test_fieldInitializerOutsideConstructor);
+      });
+      _ut.test('test_fieldInitializerOutsideConstructor_defaultParameters', () {
+        final __test = new CompileTimeErrorCodeTest();
+        runJUnitTest(__test, __test.test_fieldInitializerOutsideConstructor_defaultParameters);
+      });
       _ut.test('test_implementsNonClass', () {
         final __test = new CompileTimeErrorCodeTest();
         runJUnitTest(__test, __test.test_implementsNonClass);
@@ -1905,6 +2266,10 @@
         final __test = new CompileTimeErrorCodeTest();
         runJUnitTest(__test, __test.test_nonConstMapValue);
       });
+      _ut.test('test_rethrowOutsideCatch', () {
+        final __test = new CompileTimeErrorCodeTest();
+        runJUnitTest(__test, __test.test_rethrowOutsideCatch);
+      });
       _ut.test('test_uriWithInterpolation_constant', () {
         final __test = new CompileTimeErrorCodeTest();
         runJUnitTest(__test, __test.test_uriWithInterpolation_constant);
@@ -2005,18 +2370,18 @@
     return super.visitPrefixedIdentifier(node);
   }
   Object visitSimpleIdentifier(SimpleIdentifier node) {
-    ASTNode parent19 = node.parent;
-    if (parent19 is MethodInvocation && identical(node, ((parent19 as MethodInvocation)).methodName)) {
+    ASTNode parent21 = node.parent;
+    if (parent21 is MethodInvocation && identical(node, ((parent21 as MethodInvocation)).methodName)) {
       return null;
-    } else if (parent19 is RedirectingConstructorInvocation && identical(node, ((parent19 as RedirectingConstructorInvocation)).constructorName)) {
+    } else if (parent21 is RedirectingConstructorInvocation && identical(node, ((parent21 as RedirectingConstructorInvocation)).constructorName)) {
       return null;
-    } else if (parent19 is SuperConstructorInvocation && identical(node, ((parent19 as SuperConstructorInvocation)).constructorName)) {
+    } else if (parent21 is SuperConstructorInvocation && identical(node, ((parent21 as SuperConstructorInvocation)).constructorName)) {
       return null;
-    } else if (parent19 is ConstructorName && identical(node, ((parent19 as ConstructorName)).name)) {
+    } else if (parent21 is ConstructorName && identical(node, ((parent21 as ConstructorName)).name)) {
       return null;
-    } else if (parent19 is Label && identical(node, ((parent19 as Label)).label)) {
+    } else if (parent21 is Label && identical(node, ((parent21 as Label)).label)) {
       return null;
-    } else if (parent19 is ImportDirective && identical(node, ((parent19 as ImportDirective)).prefix)) {
+    } else if (parent21 is ImportDirective && identical(node, ((parent21 as ImportDirective)).prefix)) {
       return null;
     } else if (node.element is PrefixElement) {
       return null;
@@ -2388,9 +2753,9 @@
     SimpleIdentifier node = ASTFactory.identifier2(fieldName);
     ASTFactory.assignmentExpression(node, TokenType.EQ, ASTFactory.integer(0));
     resolveInClass(node, classA);
-    Element element50 = node.element;
-    EngineTestCase.assertInstanceOf(PropertyAccessorElement, element50);
-    JUnitTestCase.assertTrue(((element50 as PropertyAccessorElement)).isSetter());
+    Element element56 = node.element;
+    EngineTestCase.assertInstanceOf(PropertyAccessorElement, element56);
+    JUnitTestCase.assertTrue(((element56 as PropertyAccessorElement)).isSetter());
     _listener.assertNoErrors();
   }
   void test_visitSuperConstructorInvocation() {
@@ -2429,16 +2794,17 @@
     AnalysisContextImpl context = new AnalysisContextImpl();
     SourceFactory sourceFactory = new SourceFactory.con2([new DartUriResolver(DartSdk.defaultSdk)]);
     context.sourceFactory = sourceFactory;
+    FileBasedSource source = new FileBasedSource.con1(sourceFactory, FileUtilities2.createFile("/test.dart"));
     CompilationUnitElementImpl definingCompilationUnit = new CompilationUnitElementImpl("test.dart");
-    definingCompilationUnit.source = new FileBasedSource.con1(sourceFactory, FileUtilities2.createFile("/test.dart"));
+    definingCompilationUnit.source = source;
     _definingLibrary = ElementFactory.library(context, "test");
     _definingLibrary.definingCompilationUnit = definingCompilationUnit;
-    Library library = new Library(context, _listener, null);
+    Library library = new Library(context, _listener, source);
     library.libraryElement = _definingLibrary;
-    _visitor = new ResolverVisitor(library, null, _typeProvider);
+    _visitor = new ResolverVisitor(library, source, _typeProvider);
     try {
       return _visitor.elementResolver_J2DAccessor as ElementResolver;
-    } on JavaException catch (exception) {
+    } catch (exception) {
       throw new IllegalArgumentException("Could not create resolver", exception);
     }
   }
@@ -2507,7 +2873,7 @@
         _visitor.enclosingClass_J2DAccessor = null;
         _visitor.nameScope_J2DAccessor = outerScope;
       }
-    } on JavaException catch (exception) {
+    } catch (exception) {
       throw new IllegalArgumentException("Could not resolve node", exception);
     }
   }
@@ -2532,7 +2898,7 @@
       } finally {
         _visitor.nameScope_J2DAccessor = outerScope;
       }
-    } on JavaException catch (exception) {
+    } catch (exception) {
       throw new IllegalArgumentException("Could not resolve node", exception);
     }
   }
@@ -2558,7 +2924,7 @@
       } finally {
         _visitor.labelScope_J2DAccessor = outerScope;
       }
-    } on JavaException catch (exception) {
+    } catch (exception) {
       throw new IllegalArgumentException("Could not resolve node", exception);
     }
   }
@@ -3041,37 +3407,6 @@
   }
 }
 /**
- * The class {@code AnalysisContextFactory} defines utility methods used to create analysis contexts
- * for testing purposes.
- */
-class AnalysisContextFactory {
-  /**
-   * Create an analysis context that has a fake core library already resolved.
-   * @return the analysis context that was created
-   */
-  static AnalysisContextImpl contextWithCore() {
-    AnalysisContextImpl context = new AnalysisContextImpl();
-    SourceFactory sourceFactory = new SourceFactory.con2([new DartUriResolver(DartSdk.defaultSdk), new FileUriResolver()]);
-    context.sourceFactory = sourceFactory;
-    TestTypeProvider provider = new TestTypeProvider();
-    CompilationUnitElementImpl unit = new CompilationUnitElementImpl("core.dart");
-    unit.types = <ClassElement> [provider.boolType.element, provider.doubleType.element, provider.functionType.element, provider.intType.element, provider.listType.element, provider.mapType.element, provider.numType.element, provider.objectType.element, provider.stackTraceType.element, provider.stringType.element, provider.typeType.element];
-    LibraryElementImpl library = new LibraryElementImpl(context, ASTFactory.libraryIdentifier2(["dart", "core"]));
-    library.definingCompilationUnit = unit;
-    Map<Source, LibraryElement> elementMap = new Map<Source, LibraryElement>();
-    Source coreSource = sourceFactory.forUri(DartSdk.DART_CORE);
-    elementMap[coreSource] = library;
-    context.recordLibraryElements(elementMap);
-    unit.source = coreSource;
-    return context;
-  }
-  /**
-   * Prevent the creation of instances of this class.
-   */
-  AnalysisContextFactory() {
-  }
-}
-/**
  * Instances of the class {@code TestTypeProvider} implement a type provider that can be used by
  * tests without creating the element model for the core library.
  */
@@ -3249,6 +3584,45 @@
     doubleElement.methods = <MethodElement> [ElementFactory.methodElement("remainder", _doubleType, [_numType]), ElementFactory.methodElement("+", _doubleType, [_numType]), ElementFactory.methodElement("-", _doubleType, [_numType]), ElementFactory.methodElement("*", _doubleType, [_numType]), ElementFactory.methodElement("%", _doubleType, [_numType]), ElementFactory.methodElement("/", _doubleType, [_numType]), ElementFactory.methodElement("~/", _doubleType, [_numType]), ElementFactory.methodElement("-", _doubleType, []), ElementFactory.methodElement("abs", _doubleType, []), ElementFactory.methodElement("round", _doubleType, []), ElementFactory.methodElement("floor", _doubleType, []), ElementFactory.methodElement("ceil", _doubleType, []), ElementFactory.methodElement("truncate", _doubleType, []), ElementFactory.methodElement("toString", _stringType, [])];
   }
 }
+/**
+ * The class {@code AnalysisContextFactory} defines utility methods used to create analysis contexts
+ * for testing purposes.
+ */
+class AnalysisContextFactory {
+  /**
+   * Create an analysis context that has a fake core library already resolved.
+   * @return the analysis context that was created
+   */
+  static AnalysisContextImpl contextWithCore() {
+    AnalysisContextImpl context = new AnalysisContextImpl();
+    SourceFactory sourceFactory = new SourceFactory.con2([new DartUriResolver(DartSdk.defaultSdk), new FileUriResolver()]);
+    context.sourceFactory = sourceFactory;
+    TestTypeProvider provider = new TestTypeProvider();
+    CompilationUnitElementImpl coreUnit = new CompilationUnitElementImpl("core.dart");
+    Source coreSource = sourceFactory.forUri(DartSdk.DART_CORE);
+    coreUnit.source = coreSource;
+    coreUnit.types = <ClassElement> [provider.boolType.element, provider.doubleType.element, provider.functionType.element, provider.intType.element, provider.listType.element, provider.mapType.element, provider.numType.element, provider.objectType.element, provider.stackTraceType.element, provider.stringType.element, provider.typeType.element];
+    LibraryElementImpl coreLibrary = new LibraryElementImpl(context, ASTFactory.libraryIdentifier2(["dart", "core"]));
+    coreLibrary.definingCompilationUnit = coreUnit;
+    CompilationUnitElementImpl htmlUnit = new CompilationUnitElementImpl("html_dartium.dart");
+    Source htmlSource = sourceFactory.forUri(DartSdk.DART_HTML);
+    htmlUnit.source = htmlSource;
+    LibraryElementImpl htmlLibrary = new LibraryElementImpl(context, ASTFactory.libraryIdentifier2(["dart", "dom", "html"]));
+    htmlLibrary.definingCompilationUnit = htmlUnit;
+    Map<Source, LibraryElement> elementMap = new Map<Source, LibraryElement>();
+    elementMap[coreSource] = coreLibrary;
+    elementMap[htmlSource] = htmlLibrary;
+    context.setContents(coreSource, "");
+    context.setContents(htmlSource, "");
+    context.recordLibraryElements(elementMap);
+    return context;
+  }
+  /**
+   * Prevent the creation of instances of this class.
+   */
+  AnalysisContextFactory() {
+  }
+}
 class LibraryImportScopeTest extends ResolverTestCase {
   void test_conflictingImports() {
     AnalysisContext context = new AnalysisContextImpl();
@@ -3362,10 +3736,10 @@
    * structures that are expected to have been resolved have an element associated with them.
    */
   ResolutionVerifier() {
-    _jtd_constructor_319_impl();
+    _jtd_constructor_323_impl();
   }
-  _jtd_constructor_319_impl() {
-    _jtd_constructor_320_impl(null);
+  _jtd_constructor_323_impl() {
+    _jtd_constructor_324_impl(null);
   }
   /**
    * Initialize a newly created verifier to verify that all of the identifiers in the visited AST
@@ -3376,9 +3750,9 @@
    * therefore not cause the test to fail
    */
   ResolutionVerifier.con1(Set<ASTNode> knownExceptions2) {
-    _jtd_constructor_320_impl(knownExceptions2);
+    _jtd_constructor_324_impl(knownExceptions2);
   }
-  _jtd_constructor_320_impl(Set<ASTNode> knownExceptions2) {
+  _jtd_constructor_324_impl(Set<ASTNode> knownExceptions2) {
     this._knownExceptions = knownExceptions2;
   }
   /**
@@ -4074,7 +4448,7 @@
   Type2 analyze2(Expression node, InterfaceType thisType) {
     try {
       _analyzer.thisType_J2DAccessor = thisType;
-    } on JavaException catch (exception) {
+    } catch (exception) {
       throw new IllegalArgumentException("Could not set type of 'this'", exception);
     }
     node.accept(_analyzer);
@@ -4155,16 +4529,19 @@
    */
   StaticTypeAnalyzer createAnalyzer() {
     AnalysisContextImpl context = new AnalysisContextImpl();
-    context.sourceFactory = new SourceFactory.con2([new DartUriResolver(DartSdk.defaultSdk)]);
+    SourceFactory sourceFactory = new SourceFactory.con2([new DartUriResolver(DartSdk.defaultSdk)]);
+    context.sourceFactory = sourceFactory;
+    FileBasedSource source = new FileBasedSource.con1(sourceFactory, FileUtilities2.createFile("/lib.dart"));
     CompilationUnitElementImpl definingCompilationUnit = new CompilationUnitElementImpl("lib.dart");
+    definingCompilationUnit.source = source;
     LibraryElementImpl definingLibrary = new LibraryElementImpl(context, null);
     definingLibrary.definingCompilationUnit = definingCompilationUnit;
-    Library library = new Library(context, _listener, null);
+    Library library = new Library(context, _listener, source);
     library.libraryElement = definingLibrary;
-    ResolverVisitor visitor = new ResolverVisitor(library, null, _typeProvider);
+    ResolverVisitor visitor = new ResolverVisitor(library, source, _typeProvider);
     try {
       return visitor.typeAnalyzer_J2DAccessor as StaticTypeAnalyzer;
-    } on JavaException catch (exception) {
+    } catch (exception) {
       throw new IllegalArgumentException("Could not create analyzer", exception);
     }
   }
@@ -4240,12 +4617,12 @@
    */
   void setType(FormalParameter parameter, Type2 type38) {
     SimpleIdentifier identifier17 = parameter.identifier;
-    Element element51 = identifier17.element;
-    if (element51 is! ParameterElement) {
-      element51 = new ParameterElementImpl(identifier17);
-      identifier17.element = element51;
+    Element element57 = identifier17.element;
+    if (element57 is! ParameterElement) {
+      element57 = new ParameterElementImpl(identifier17);
+      identifier17.element = element57;
     }
-    ((element51 as ParameterElementImpl)).type = type38;
+    ((element57 as ParameterElementImpl)).type = type38;
   }
   static dartSuite() {
     _ut.group('StaticTypeAnalyzerTest', () {
@@ -4504,7 +4881,7 @@
   void test_define_duplicate() {
     LibraryElement definingLibrary2 = createTestLibrary();
     GatheringErrorListener errorListener2 = new GatheringErrorListener();
-    Scope rootScope = new Scope_10(definingLibrary2, errorListener2);
+    Scope rootScope = new Scope_12(definingLibrary2, errorListener2);
     EnclosedScope scope = new EnclosedScope(rootScope);
     VariableElement element1 = ElementFactory.localVariableElement(ASTFactory.identifier2("v1"));
     VariableElement element2 = ElementFactory.localVariableElement(ASTFactory.identifier2("v1"));
@@ -4515,7 +4892,7 @@
   void test_define_normal() {
     LibraryElement definingLibrary3 = createTestLibrary();
     GatheringErrorListener errorListener3 = new GatheringErrorListener();
-    Scope rootScope = new Scope_11(definingLibrary3, errorListener3);
+    Scope rootScope = new Scope_13(definingLibrary3, errorListener3);
     EnclosedScope outerScope = new EnclosedScope(rootScope);
     EnclosedScope innerScope = new EnclosedScope(outerScope);
     VariableElement element1 = ElementFactory.localVariableElement(ASTFactory.identifier2("v1"));
@@ -4537,18 +4914,18 @@
     });
   }
 }
-class Scope_10 extends Scope {
+class Scope_12 extends Scope {
   LibraryElement definingLibrary2;
   GatheringErrorListener errorListener2;
-  Scope_10(this.definingLibrary2, this.errorListener2) : super();
+  Scope_12(this.definingLibrary2, this.errorListener2) : super();
   LibraryElement get definingLibrary => definingLibrary2;
   AnalysisErrorListener get errorListener => errorListener2;
   Element lookup3(String name, LibraryElement referencingLibrary) => null;
 }
-class Scope_11 extends Scope {
+class Scope_13 extends Scope {
   LibraryElement definingLibrary3;
   GatheringErrorListener errorListener3;
-  Scope_11(this.definingLibrary3, this.errorListener3) : super();
+  Scope_13(this.definingLibrary3, this.errorListener3) : super();
   LibraryElement get definingLibrary => definingLibrary3;
   AnalysisErrorListener get errorListener => errorListener3;
   Element lookup3(String name, LibraryElement referencingLibrary) => null;
@@ -4798,90 +5175,12 @@
     assertNoErrors();
     verify([source]);
   }
-  void test_argumentDefinitionTestNonParameter_formalParameter() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["f(var v) {", "  return ?v;", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_argumentDefinitionTestNonParameter_namedParameter() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["f({var v : 0}) {", "  return ?v;", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_argumentDefinitionTestNonParameter_optionalParameter() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["f([var v]) {", "  return ?v;", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_breakWithoutLabelInSwitch() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  void m(int i) {", "    switch (i) {", "      case 0:", "        break;", "    }", "  }", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_builtInIdentifierAsType_dynamic() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  dynamic x;", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_caseExpressionTypeImplementsEquals_int() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["f(int i) {", "  switch(i) {", "    case(1) : return 1;", "    default: return 0;", "  }", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_caseExpressionTypeImplementsEquals_Object() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class IntWrapper {", "  final int value;", "  const IntWrapper(this.value);", "}", "", "f(IntWrapper intWrapper) {", "  switch(intWrapper) {", "    case(const IntWrapper(1)) : return 1;", "    default: return 0;", "  }", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_caseExpressionTypeImplementsEquals_String() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["f(String s) {", "  switch(s) {", "    case('1') : return 1;", "    default: return 0;", "  }", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
   void test_class_extends_implements() {
     Source source = addSource("/test.dart", EngineTestCase.createSource(["class A extends B implements C {}", "class B {}", "class C {}"]));
     resolve(source, []);
     assertNoErrors();
     verify([source]);
   }
-  void test_constConstructorWithNonFinalField_const() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  const int x;", "  const A() {}", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_constConstructorWithNonFinalField_final() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  final int x;", "  const A() {}", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_constConstructorWithNonFinalField_syntheticField() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  const A();", "  set x(value) {}", "  get x {return 0;}", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_defaultValueInFunctionTypeAlias() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["typedef F([x]);"]));
-    resolve(source, []);
-    assertErrors([]);
-    verify([source]);
-  }
-  void test_duplicateDefinition_getter() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["bool get a => true;"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
   void test_empty() {
     Source source = addSource("/test.dart", "");
     resolve(source, []);
@@ -4924,36 +5223,6 @@
     assertErrors([StaticTypeWarningCode.INVALID_ASSIGNMENT]);
     verify([source]);
   }
-  void test_invalidAssignment() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  var x;", "  var y;", "  x = y;", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_invalidAssignment_toDynamic() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  var g;", "  g = () => 0;", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_invocationOfNonFunction_dynamic() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  var f;", "}", "class B extends A {", "  g() {", "    f();", "  }", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_invocationOfNonFunction_getter() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  var g;", "}", "f() {", "  A a;", "  a.g();", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_invocationOfNonFunction_localVariable() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  var g;", "  g();", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
   void test_invoke_dynamicThroughGetter() {
     Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  List get X => [() => 0];", "  m(A a) {", "    X.last();", "  }", "}"]));
     resolve(source, []);
@@ -5020,118 +5289,18 @@
     assertNoErrors();
     verify([source]);
   }
-  void test_newWithAbstractClass_factory() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["abstract class A {", "  factory A() { return new B(); }", "}", "class B implements A {", "  B() {}", "}", "A f() {", "  return new A();", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_nonBoolExpression_assert_bool() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["f() {", "  assert(true);", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_nonBoolExpression_assert_functionType() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["bool makeAssertion() => true;", "f() {", "  assert(makeAssertion);", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
   void test_resolveAgainstNull() {
     Source source = addSource("/test.dart", EngineTestCase.createSource(["f(var p) {", "  return null == p;", "}"]));
     resolve(source, []);
     assertNoErrors();
     verify([source]);
   }
-  void test_returnOfInvalidType_dynamic() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {", "  static void testLogicalOp() {", "    testOr(a, b, onTypeError) {", "      try {", "        return a || b;", "      } on TypeError catch (t) {", "        return onTypeError;", "      }", "    }", "  }", "}"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_returnOfInvalidType_subtype() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {}", "class B extends A {}", "A f(B b) { return b; }"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_returnOfInvalidType_supertype() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {}", "class B extends A {}", "B f(A a) { return a; }"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_typeArgumentNotMatchingBounds_const() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {}", "class B extends A {}", "class G<E extends A> {", "  const G() {}", "}", "f() { return const G<B>(); }"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
-  void test_typeArgumentNotMatchingBounds_new() {
-    Source source = addSource("/test.dart", EngineTestCase.createSource(["class A {}", "class B extends A {}", "class G<E extends A> {}", "f() { return new G<B>(); }"]));
-    resolve(source, []);
-    assertNoErrors();
-    verify([source]);
-  }
   static dartSuite() {
     _ut.group('SimpleResolverTest', () {
-      _ut.test('test_argumentDefinitionTestNonParameter_formalParameter', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_argumentDefinitionTestNonParameter_formalParameter);
-      });
-      _ut.test('test_argumentDefinitionTestNonParameter_namedParameter', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_argumentDefinitionTestNonParameter_namedParameter);
-      });
-      _ut.test('test_argumentDefinitionTestNonParameter_optionalParameter', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_argumentDefinitionTestNonParameter_optionalParameter);
-      });
-      _ut.test('test_breakWithoutLabelInSwitch', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_breakWithoutLabelInSwitch);
-      });
-      _ut.test('test_builtInIdentifierAsType_dynamic', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_builtInIdentifierAsType_dynamic);
-      });
-      _ut.test('test_caseExpressionTypeImplementsEquals_Object', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_caseExpressionTypeImplementsEquals_Object);
-      });
-      _ut.test('test_caseExpressionTypeImplementsEquals_String', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_caseExpressionTypeImplementsEquals_String);
-      });
-      _ut.test('test_caseExpressionTypeImplementsEquals_int', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_caseExpressionTypeImplementsEquals_int);
-      });
       _ut.test('test_class_extends_implements', () {
         final __test = new SimpleResolverTest();
         runJUnitTest(__test, __test.test_class_extends_implements);
       });
-      _ut.test('test_constConstructorWithNonFinalField_const', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_constConstructorWithNonFinalField_const);
-      });
-      _ut.test('test_constConstructorWithNonFinalField_final', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_constConstructorWithNonFinalField_final);
-      });
-      _ut.test('test_constConstructorWithNonFinalField_syntheticField', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_constConstructorWithNonFinalField_syntheticField);
-      });
-      _ut.test('test_defaultValueInFunctionTypeAlias', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_defaultValueInFunctionTypeAlias);
-      });
-      _ut.test('test_duplicateDefinition_getter', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_duplicateDefinition_getter);
-      });
       _ut.test('test_empty', () {
         final __test = new SimpleResolverTest();
         runJUnitTest(__test, __test.test_empty);
@@ -5160,26 +5329,6 @@
         final __test = new SimpleResolverTest();
         runJUnitTest(__test, __test.test_indexExpression_typeParameters_invalidAssignmentWarning);
       });
-      _ut.test('test_invalidAssignment', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_invalidAssignment);
-      });
-      _ut.test('test_invalidAssignment_toDynamic', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_invalidAssignment_toDynamic);
-      });
-      _ut.test('test_invocationOfNonFunction_dynamic', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_invocationOfNonFunction_dynamic);
-      });
-      _ut.test('test_invocationOfNonFunction_getter', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_invocationOfNonFunction_getter);
-      });
-      _ut.test('test_invocationOfNonFunction_localVariable', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_invocationOfNonFunction_localVariable);
-      });
       _ut.test('test_invoke_dynamicThroughGetter', () {
         final __test = new SimpleResolverTest();
         runJUnitTest(__test, __test.test_invoke_dynamicThroughGetter);
@@ -5208,42 +5357,10 @@
         final __test = new SimpleResolverTest();
         runJUnitTest(__test, __test.test_methodCascades_withSetter);
       });
-      _ut.test('test_newWithAbstractClass_factory', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_newWithAbstractClass_factory);
-      });
-      _ut.test('test_nonBoolExpression_assert_bool', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_nonBoolExpression_assert_bool);
-      });
-      _ut.test('test_nonBoolExpression_assert_functionType', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_nonBoolExpression_assert_functionType);
-      });
       _ut.test('test_resolveAgainstNull', () {
         final __test = new SimpleResolverTest();
         runJUnitTest(__test, __test.test_resolveAgainstNull);
       });
-      _ut.test('test_returnOfInvalidType_dynamic', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_returnOfInvalidType_dynamic);
-      });
-      _ut.test('test_returnOfInvalidType_subtype', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_returnOfInvalidType_subtype);
-      });
-      _ut.test('test_returnOfInvalidType_supertype', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_returnOfInvalidType_supertype);
-      });
-      _ut.test('test_typeArgumentNotMatchingBounds_const', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_typeArgumentNotMatchingBounds_const);
-      });
-      _ut.test('test_typeArgumentNotMatchingBounds_new', () {
-        final __test = new SimpleResolverTest();
-        runJUnitTest(__test, __test.test_typeArgumentNotMatchingBounds_new);
-      });
     });
   }
 }
@@ -5260,6 +5377,7 @@
 //  ScopeTest.dartSuite();
 //  CompileTimeErrorCodeTest.dartSuite();
 //  ErrorResolverTest.dartSuite();
+//  NonErrorResolverTest.dartSuite();
 //  SimpleResolverTest.dartSuite();
 //  StaticTypeWarningCodeTest.dartSuite();
 //  StaticWarningCodeTest.dartSuite();
diff --git a/pkg/analyzer_experimental/test/generated/scanner_test.dart b/pkg/analyzer_experimental/test/generated/scanner_test.dart
index 994cca8..4f0fe36 100644
--- a/pkg/analyzer_experimental/test/generated/scanner_test.dart
+++ b/pkg/analyzer_experimental/test/generated/scanner_test.dart
@@ -419,6 +419,10 @@
         final __test = new CharBufferScannerTest();
         runJUnitTest(__test, __test.test_keyword_else);
       });
+      _ut.test('test_keyword_enum', () {
+        final __test = new CharBufferScannerTest();
+        runJUnitTest(__test, __test.test_keyword_enum);
+      });
       _ut.test('test_keyword_export', () {
         final __test = new CharBufferScannerTest();
         runJUnitTest(__test, __test.test_keyword_export);
@@ -491,6 +495,10 @@
         final __test = new CharBufferScannerTest();
         runJUnitTest(__test, __test.test_keyword_part);
       });
+      _ut.test('test_keyword_rethrow', () {
+        final __test = new CharBufferScannerTest();
+        runJUnitTest(__test, __test.test_keyword_rethrow);
+      });
       _ut.test('test_keyword_return', () {
         final __test = new CharBufferScannerTest();
         runJUnitTest(__test, __test.test_keyword_return);
@@ -1058,6 +1066,10 @@
         final __test = new StringScannerTest();
         runJUnitTest(__test, __test.test_keyword_else);
       });
+      _ut.test('test_keyword_enum', () {
+        final __test = new StringScannerTest();
+        runJUnitTest(__test, __test.test_keyword_enum);
+      });
       _ut.test('test_keyword_export', () {
         final __test = new StringScannerTest();
         runJUnitTest(__test, __test.test_keyword_export);
@@ -1130,6 +1142,10 @@
         final __test = new StringScannerTest();
         runJUnitTest(__test, __test.test_keyword_part);
       });
+      _ut.test('test_keyword_rethrow', () {
+        final __test = new StringScannerTest();
+        runJUnitTest(__test, __test.test_keyword_rethrow);
+      });
       _ut.test('test_keyword_return', () {
         final __test = new StringScannerTest();
         runJUnitTest(__test, __test.test_keyword_return);
@@ -1676,6 +1692,9 @@
   void test_keyword_else() {
     assertKeywordToken("else");
   }
+  void test_keyword_enum() {
+    assertKeywordToken("enum");
+  }
   void test_keyword_export() {
     assertKeywordToken("export");
   }
@@ -1730,6 +1749,9 @@
   void test_keyword_part() {
     assertKeywordToken("part");
   }
+  void test_keyword_rethrow() {
+    assertKeywordToken("rethrow");
+  }
   void test_keyword_return() {
     assertKeywordToken("return");
   }
diff --git a/pkg/analyzer_experimental/test/generated/test_support.dart b/pkg/analyzer_experimental/test/generated/test_support.dart
index 4ca21f2..cf2e434 100644
--- a/pkg/analyzer_experimental/test/generated/test_support.dart
+++ b/pkg/analyzer_experimental/test/generated/test_support.dart
@@ -45,17 +45,17 @@
    * Initialize a newly created error listener to collect errors.
    */
   GatheringErrorListener() : super() {
-    _jtd_constructor_317_impl();
+    _jtd_constructor_321_impl();
   }
-  _jtd_constructor_317_impl() {
+  _jtd_constructor_321_impl() {
   }
   /**
    * Initialize a newly created error listener to collect errors.
    */
   GatheringErrorListener.con1(String rawSource2) {
-    _jtd_constructor_318_impl(rawSource2);
+    _jtd_constructor_322_impl(rawSource2);
   }
-  _jtd_constructor_318_impl(String rawSource2) {
+  _jtd_constructor_322_impl(String rawSource2) {
     this._rawSource = rawSource2;
     this._markedSource = rawSource2;
   }
@@ -275,15 +275,15 @@
     writer.print(expectedErrors.length);
     writer.print(" errors:");
     for (AnalysisError error in expectedErrors) {
-      Source source13 = error.source;
-      LineInfo lineInfo = _lineInfoMap[source13];
+      Source source11 = error.source;
+      LineInfo lineInfo = _lineInfoMap[source11];
       writer.println();
       if (lineInfo == null) {
         int offset10 = error.offset;
-        writer.printf("  %s %s (%d..%d)", [source13 == null ? "" : source13.shortName, error.errorCode, offset10, offset10 + error.length]);
+        writer.printf("  %s %s (%d..%d)", [source11 == null ? "" : source11.shortName, error.errorCode, offset10, offset10 + error.length]);
       } else {
         LineInfo_Location location = lineInfo.getLocation(error.offset);
-        writer.printf("  %s %s (%d, %d/%d)", [source13 == null ? "" : source13.shortName, error.errorCode, location.lineNumber, location.columnNumber, error.length]);
+        writer.printf("  %s %s (%d, %d/%d)", [source11 == null ? "" : source11.shortName, error.errorCode, location.lineNumber, location.columnNumber, error.length]);
       }
     }
     writer.println();
@@ -291,15 +291,15 @@
     writer.print(_errors.length);
     writer.print(" errors:");
     for (AnalysisError error in _errors) {
-      Source source14 = error.source;
-      LineInfo lineInfo = _lineInfoMap[source14];
+      Source source12 = error.source;
+      LineInfo lineInfo = _lineInfoMap[source12];
       writer.println();
       if (lineInfo == null) {
         int offset11 = error.offset;
-        writer.printf("  %s %s (%d..%d): %s", [source14 == null ? "" : source14.shortName, error.errorCode, offset11, offset11 + error.length, error.message]);
+        writer.printf("  %s %s (%d..%d): %s", [source12 == null ? "" : source12.shortName, error.errorCode, offset11, offset11 + error.length, error.message]);
       } else {
         LineInfo_Location location = lineInfo.getLocation(error.offset);
-        writer.printf("  %s %s (%d, %d/%d): %s", [source14 == null ? "" : source14.shortName, error.errorCode, location.lineNumber, location.columnNumber, error.length, error.message]);
+        writer.printf("  %s %s (%d, %d/%d): %s", [source12 == null ? "" : source12.shortName, error.errorCode, location.lineNumber, location.columnNumber, error.length, error.message]);
       }
     }
     JUnitTestCase.fail(writer.toString());
diff --git a/pkg/fixnum/test/int_64_vm_test.dart b/pkg/fixnum/test/int_64_vm_test.dart
index b9b4a9a..b9d0f70 100644
--- a/pkg/fixnum/test/int_64_vm_test.dart
+++ b/pkg/fixnum/test/int_64_vm_test.dart
@@ -5,11 +5,12 @@
 // A test to compare the results of the fixnum library with the Dart VM
 
 library int64vmtest;
+
 import 'dart:math' as math;
 
-part '../lib/src/int32.dart';
-part '../lib/src/int64.dart';
-part '../lib/src/intx.dart';
+part 'package:fixnum/src/int32.dart';
+part 'package:fixnum/src/int64.dart';
+part 'package:fixnum/src/intx.dart';
 
 final random = new math.Random();
 
diff --git a/pkg/http/lib/http.dart b/pkg/http/lib/http.dart
index dde9f29..8a61f6e 100644
--- a/pkg/http/lib/http.dart
+++ b/pkg/http/lib/http.dart
@@ -54,7 +54,7 @@
 library http;
 
 import 'dart:async';
-import 'dart:scalarlist';
+import 'dart:typeddata';
 import 'dart:uri';
 
 import 'src/client.dart';
diff --git a/pkg/http/lib/src/base_client.dart b/pkg/http/lib/src/base_client.dart
index cda7b0d..eb9fca7 100644
--- a/pkg/http/lib/src/base_client.dart
+++ b/pkg/http/lib/src/base_client.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 import 'dart:io';
-import 'dart:scalarlist';
+import 'dart:typeddata';
 import 'dart:uri';
 
 import 'base_request.dart';
diff --git a/pkg/http/lib/src/byte_stream.dart b/pkg/http/lib/src/byte_stream.dart
index 96af221..b53b8eb 100644
--- a/pkg/http/lib/src/byte_stream.dart
+++ b/pkg/http/lib/src/byte_stream.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 import 'dart:io';
-import 'dart:scalarlist';
+import 'dart:typeddata';
 
 import 'utils.dart';
 
diff --git a/pkg/http/lib/src/client.dart b/pkg/http/lib/src/client.dart
index 204109e..302b8c7 100644
--- a/pkg/http/lib/src/client.dart
+++ b/pkg/http/lib/src/client.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 import 'dart:io';
-import 'dart:scalarlist';
+import 'dart:typeddata';
 
 import 'base_client.dart';
 import 'base_request.dart';
diff --git a/pkg/http/lib/src/multipart_file.dart b/pkg/http/lib/src/multipart_file.dart
index 2f1f102..5e5bbb3 100644
--- a/pkg/http/lib/src/multipart_file.dart
+++ b/pkg/http/lib/src/multipart_file.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import 'byte_stream.dart';
 import 'utils.dart';
diff --git a/pkg/http/lib/src/request.dart b/pkg/http/lib/src/request.dart
index 525f1ae..9d68508 100644
--- a/pkg/http/lib/src/request.dart
+++ b/pkg/http/lib/src/request.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 import 'dart:io';
-import 'dart:scalarlist';
+import 'dart:typeddata';
 import 'dart:uri';
 
 import 'base_request.dart';
diff --git a/pkg/http/lib/src/response.dart b/pkg/http/lib/src/response.dart
index b6d910e..2376f72 100644
--- a/pkg/http/lib/src/response.dart
+++ b/pkg/http/lib/src/response.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 import 'dart:io';
-import 'dart:scalarlist';
+import 'dart:typeddata';
 
 import 'base_request.dart';
 import 'base_response.dart';
diff --git a/pkg/http/lib/src/utils.dart b/pkg/http/lib/src/utils.dart
index 5a69ee5..25b0022 100644
--- a/pkg/http/lib/src/utils.dart
+++ b/pkg/http/lib/src/utils.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:crypto';
 import 'dart:io';
-import 'dart:scalarlist';
+import 'dart:typeddata';
 import 'dart:uri';
 import 'dart:utf';
 
@@ -116,8 +116,7 @@
 /// [ByteArrayViewable], this just returns a view on [input].
 Uint8List toUint8List(List<int> input) {
   if (input is Uint8List) return input;
-  if (input is ByteArrayViewable) input = input.asByteArray();
-  if (input is ByteArray) return new Uint8List.view(input);
+  if (input is ByteData) return new Uint8List.view(input.buffer);
   var output = new Uint8List(input.length);
   output.setRange(0, input.length, input);
   return output;
diff --git a/pkg/http/pubspec.yaml b/pkg/http/pubspec.yaml
index 66cd21a..e275dd6 100644
--- a/pkg/http/pubspec.yaml
+++ b/pkg/http/pubspec.yaml
@@ -2,5 +2,7 @@
 author: "Dart Team <misc@dartlang.org>"
 homepage: http://www.dartlang.org
 description: A composable, Future-based API for making HTTP requests.
+dependencies:
+  pathos: any
 dev_dependencies:
   unittest: any
diff --git a/pkg/http/test/client_test.dart b/pkg/http/test/client_test.dart
index 27cd0b9..daa3acb 100644
--- a/pkg/http/test/client_test.dart
+++ b/pkg/http/test/client_test.dart
@@ -7,9 +7,10 @@
 import 'dart:io';
 import 'dart:uri';
 
+import 'package:http/http.dart' as http;
+import 'package:http/src/utils.dart';
 import 'package:unittest/unittest.dart';
-import '../lib/src/utils.dart';
-import '../lib/http.dart' as http;
+
 import 'utils.dart';
 
 void main() {
diff --git a/pkg/http/test/http_test.dart b/pkg/http/test/http_test.dart
index 2dd5d3e..81cca76 100644
--- a/pkg/http/test/http_test.dart
+++ b/pkg/http/test/http_test.dart
@@ -6,8 +6,9 @@
 
 import 'dart:io';
 
+import 'package:http/http.dart' as http;
 import 'package:unittest/unittest.dart';
-import '../lib/http.dart' as http;
+
 import 'utils.dart';
 
 main() {
diff --git a/pkg/http/test/mock_client_test.dart b/pkg/http/test/mock_client_test.dart
index 0c3c578..f1f75bf 100644
--- a/pkg/http/test/mock_client_test.dart
+++ b/pkg/http/test/mock_client_test.dart
@@ -9,10 +9,11 @@
 import 'dart:json' as json;
 import 'dart:uri';
 
+import 'package:http/http.dart' as http;
+import 'package:http/src/utils.dart';
+import 'package:http/testing.dart';
 import 'package:unittest/unittest.dart';
-import '../lib/http.dart' as http;
-import '../lib/testing.dart';
-import '../lib/src/utils.dart';
+
 import 'utils.dart';
 
 void main() {
diff --git a/pkg/http/test/multipart_test.dart b/pkg/http/test/multipart_test.dart
index b8210d2..e7ea1e5 100644
--- a/pkg/http/test/multipart_test.dart
+++ b/pkg/http/test/multipart_test.dart
@@ -8,10 +8,10 @@
 import 'dart:io';
 import 'dart:utf';
 
+import 'package:http/http.dart' as http;
+import 'package:http/src/utils.dart';
+import 'package:pathos/path.dart' as path;
 import 'package:unittest/unittest.dart';
-import '../../pathos/lib/path.dart' as path;
-import '../lib/http.dart' as http;
-import '../lib/src/utils.dart';
 
 import 'utils.dart';
 
diff --git a/pkg/http/test/request_test.dart b/pkg/http/test/request_test.dart
index 1ef7230..ea49199 100644
--- a/pkg/http/test/request_test.dart
+++ b/pkg/http/test/request_test.dart
@@ -6,9 +6,10 @@
 
 import 'dart:io';
 
+import 'package:http/http.dart' as http;
+import 'package:http/src/utils.dart';
 import 'package:unittest/unittest.dart';
-import '../lib/http.dart' as http;
-import '../lib/src/utils.dart';
+
 import 'utils.dart';
 
 void main() {
diff --git a/pkg/http/test/response_test.dart b/pkg/http/test/response_test.dart
index 097e0f8..17b2b60 100644
--- a/pkg/http/test/response_test.dart
+++ b/pkg/http/test/response_test.dart
@@ -7,8 +7,8 @@
 import 'dart:async';
 import 'dart:io';
 
+import 'package:http/http.dart' as http;
 import 'package:unittest/unittest.dart';
-import '../lib/http.dart' as http;
 
 void main() {
   group('()', () {
diff --git a/pkg/http/test/streamed_request_test.dart b/pkg/http/test/streamed_request_test.dart
index 6a62bdc..bebad32 100644
--- a/pkg/http/test/streamed_request_test.dart
+++ b/pkg/http/test/streamed_request_test.dart
@@ -6,8 +6,9 @@
 
 import 'dart:io';
 
+import 'package:http/http.dart' as http;
 import 'package:unittest/unittest.dart';
-import '../lib/http.dart' as http;
+
 import 'utils.dart';
 
 void main() {
diff --git a/pkg/http/test/utils.dart b/pkg/http/test/utils.dart
index 6bbe139..ab3f5f6 100644
--- a/pkg/http/test/utils.dart
+++ b/pkg/http/test/utils.dart
@@ -9,10 +9,11 @@
 import 'dart:json' as json;
 import 'dart:uri';
 
+import 'package:http/http.dart' as http;
+import 'package:http/src/byte_stream.dart';
+import 'package:http/src/utils.dart';
 import 'package:unittest/unittest.dart';
-import '../lib/src/byte_stream.dart';
-import '../lib/http.dart' as http;
-import '../lib/src/utils.dart';
+
 import 'safe_http_server.dart';
 
 /// The current server instance.
diff --git a/pkg/logging/lib/logging.dart b/pkg/logging/lib/logging.dart
index 1bf617c..d2610b1 100644
--- a/pkg/logging/lib/logging.dart
+++ b/pkg/logging/lib/logging.dart
@@ -11,8 +11,6 @@
 
 import 'dart:async';
 
-import '../../meta/lib/meta.dart';
-
 /**
  * Whether to allow fine-grain logging and configuration of loggers in a
  * hierarchy. When false, all logging is merged in the root logger.
@@ -50,9 +48,6 @@
   /** Controller used to notify when log entries are added to this logger. */
   StreamController<LogRecord> _controller;
 
-  // TODO(sigmund): remove together with the deprecated [on] API.
-  Map<LoggerHandler, StreamSubscription> _deprecatedSubscriptions;
-
   /**
    * Singleton constructor. Calling `new Logger(name)` will return the same
    * actual instance whenever it is called with the same string name.
@@ -112,17 +107,6 @@
   }
 
   /**
-   * Returns an event manager for this [Logger]. You can listen for log messages
-   * by adding a [LoggerHandler] to an event from the event manager, for
-   * instance:
-   *    logger.on.record.add((record) { ... });
-   *
-   * This API is Deprecated. Use [onRecord] instead.
-   */
-  @deprecated
-  LoggerEvents get on => new LoggerEvents(this);
-
-  /**
    * Returns an stream of messages added to this [Logger]. You can listen for
    * messages using the standard stream APIs, for instance:
    *    logger.onRecord.listen((record) { ... });
@@ -201,27 +185,6 @@
     }
   }
 
-  /** Adds a handler to listen whenever a log record is added to this logger. */
-  void _addHandler(LoggerHandler handler) {
-    if (_deprecatedSubscriptions == null) {
-      _deprecatedSubscriptions = new Map<LoggerHandler, StreamSubscription>();
-    }
-
-    _deprecatedSubscriptions[handler] = onRecord.listen(handler);
-  }
-
-  void _removeHandler(LoggerHandler handler) {
-    if (_deprecatedSubscriptions != null) {
-      var sub = _deprecatedSubscriptions.remove(handler);
-      if (sub != null) {
-        sub.cancel();
-      }
-      if (_deprecatedSubscriptions.isEmpty) {
-        _deprecatedSubscriptions = null;
-      }
-    }
-  }
-
   void _publish(LogRecord record) {
     if (_controller != null) {
       _controller.add(record);
@@ -239,30 +202,6 @@
 /** Handler callback to process log entries as they are added to a [Logger]. */
 typedef void LoggerHandler(LogRecord);
 
-
-/** Event manager for a [Logger] (holds events that a [Logger] can fire). */
-class LoggerEvents {
-  final Logger _logger;
-
-  LoggerEvents(this._logger);
-
-  /** Event fired when a log record is added to a [Logger]. */
-  LoggerHandlerList get record => new LoggerHandlerList(_logger);
-}
-
-
-/** List of handlers that will be called on a logger event. */
-class LoggerHandlerList {
-  Logger _logger;
-
-  LoggerHandlerList(this._logger);
-
-  void add(LoggerHandler handler) => _logger._addHandler(handler);
-  void remove(LoggerHandler handler) => _logger._removeHandler(handler);
-  void clear() => _logger.clearListeners();
-}
-
-
 /**
  * [Level]s to control logging output. Logging can be enabled to include all
  * levels above certain [Level]. [Level]s are ordered using an integer
diff --git a/pkg/logging/pubspec.yaml b/pkg/logging/pubspec.yaml
index 16c4428..37ed46e 100644
--- a/pkg/logging/pubspec.yaml
+++ b/pkg/logging/pubspec.yaml
@@ -1,13 +1,7 @@
 name: logging
-author: "Dart Team <misc@dartlang.org>"
+author: Dart Team <misc@dartlang.org>
+description: Provides APIs for debugging and error logging. This library introduces abstractions similar to those used in other languages, such as the Closure JS Logger and java.util.logging.Logger.
 homepage: http://www.dartlang.org
 documentation: http://api.dartlang.org/docs/pkg/logging
-description: >
- Provides APIs for debugging and error logging. This library introduces
- abstractions similar to those used in other languages, such as the Closure JS
- Logger and java.util.logging.Logger.
-
-dependencies:
-  meta: any
 dev_dependencies:
   unittest: any
diff --git a/pkg/logging/test/logging_deprecated_test.dart b/pkg/logging/test/logging_deprecated_test.dart
deleted file mode 100644
index 10ab616..0000000
--- a/pkg/logging/test/logging_deprecated_test.dart
+++ /dev/null
@@ -1,336 +0,0 @@
-// Copyright (c) 2012, 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 logging_test;
-
-import '../../../pkg/logging/lib/logging.dart';
-import 'package:unittest/unittest.dart';
-
-main() {
-  test('level comparison is a valid comparator', () {
-    var level1 = const Level('NOT_REAL1', 253);
-    expect(level1 == level1, isTrue);
-    expect(level1 <= level1, isTrue);
-    expect(level1 >= level1, isTrue);
-    expect(level1 < level1, isFalse);
-    expect(level1 > level1, isFalse);
-
-    var level2 = const Level('NOT_REAL2', 455);
-    expect(level1 <= level2, isTrue);
-    expect(level1 < level2, isTrue);
-    expect(level2 >= level1, isTrue);
-    expect(level2 > level1, isTrue);
-
-    var level3 = const Level('NOT_REAL3', 253);
-    expect(!identical(level1, level3), isTrue); // different instances
-    expect(level1 == level3, isTrue); // same value.
-  });
-
-  test('default levels are in order', () {
-    final levels = const [
-        Level.ALL, Level.FINEST, Level.FINER, Level.FINE, Level.CONFIG,
-        Level.INFO, Level.WARNING, Level.SEVERE, Level.SHOUT, Level.OFF
-      ];
-
-    for (int i = 0; i < levels.length; i++) {
-      for (int j = i + 1; j < levels.length; j++) {
-        expect(levels[i] < levels[j], isTrue);
-      }
-    }
-  });
-
-  test('levels are comparable', () {
-    final unsorted = [
-        Level.INFO, Level.CONFIG, Level.FINE, Level.SHOUT, Level.OFF,
-        Level.FINER, Level.ALL, Level.WARNING, Level.FINEST,  Level.SEVERE,
-      ];
-    final sorted = const [
-        Level.ALL, Level.FINEST, Level.FINER, Level.FINE, Level.CONFIG,
-        Level.INFO, Level.WARNING, Level.SEVERE, Level.SHOUT, Level.OFF
-      ];
-    expect(unsorted, isNot(orderedEquals(sorted)));
-
-    unsorted.sort((a, b) => a.compareTo(b));
-    expect(unsorted, orderedEquals(sorted));
-  });
-
-  test('levels are hashable', () {
-    var map = new Map<Level, String>();
-    map[Level.INFO] = 'info';
-    map[Level.SHOUT] = 'shout';
-    expect(map[Level.INFO], equals('info'));
-    expect(map[Level.SHOUT], equals('shout'));
-  });
-
-  test('logger name cannot start with a "." ', () {
-    expect(() => new Logger('.c'), throws);
-  });
-
-  test('logger naming is hierarchical', () {
-    Logger c = new Logger('a.b.c');
-    expect(c.name, equals('c'));
-    expect(c.parent.name, equals('b'));
-    expect(c.parent.parent.name, equals('a'));
-    expect(c.parent.parent.parent.name, equals(''));
-    expect(c.parent.parent.parent.parent, isNull);
-  });
-
-  test('logger full name', () {
-    Logger c = new Logger('a.b.c');
-    expect(c.fullName, equals('a.b.c'));
-    expect(c.parent.fullName, equals('a.b'));
-    expect(c.parent.parent.fullName, equals('a'));
-    expect(c.parent.parent.parent.fullName, equals(''));
-    expect(c.parent.parent.parent.parent, isNull);
-  });
-
-  test('logger parent-child links are correct', () {
-    Logger a = new Logger('a');
-    Logger b = new Logger('a.b');
-    Logger c = new Logger('a.c');
-    expect(a == b.parent, isTrue);
-    expect(a == c.parent, isTrue);
-    expect(a.children['b'] == b, isTrue);
-    expect(a.children['c'] == c, isTrue);
-  });
-
-  test('loggers are singletons', () {
-    Logger a1 = new Logger('a');
-    Logger a2 = new Logger('a');
-    Logger b = new Logger('a.b');
-    Logger root = Logger.root;
-    expect(identical(a1, a2), isTrue);
-    expect(identical(a1, b.parent), isTrue);
-    expect(identical(root, a1.parent), isTrue);
-    expect(identical(root, new Logger('')), isTrue);
-  });
-
-  group('mutating levels', () {
-    Logger root = Logger.root;
-    Logger a = new Logger('a');
-    Logger b = new Logger('a.b');
-    Logger c = new Logger('a.b.c');
-    Logger d = new Logger('a.b.c.d');
-    Logger e = new Logger('a.b.c.d.e');
-
-    setUp(() {
-      hierarchicalLoggingEnabled = true;
-      root.level = Level.INFO;
-      a.level = null;
-      b.level = null;
-      c.level = null;
-      d.level = null;
-      e.level = null;
-      root.on.record.clear();
-      a.on.record.clear();
-      b.on.record.clear();
-      c.on.record.clear();
-      d.on.record.clear();
-      e.on.record.clear();
-      hierarchicalLoggingEnabled = false;
-      root.level = Level.INFO;
-    });
-
-    test('cannot set level if hierarchy is disabled', () {
-      expect(() {a.level = Level.FINE;}, throws);
-    });
-
-    test('loggers effective level - no hierarchy', () {
-      expect(root.level, equals(Level.INFO));
-      expect(a.level, equals(Level.INFO));
-      expect(b.level, equals(Level.INFO));
-
-      root.level = Level.SHOUT;
-
-      expect(root.level, equals(Level.SHOUT));
-      expect(a.level, equals(Level.SHOUT));
-      expect(b.level, equals(Level.SHOUT));
-    });
-
-    test('loggers effective level - with hierarchy', () {
-      hierarchicalLoggingEnabled = true;
-      expect(root.level, equals(Level.INFO));
-      expect(a.level, equals(Level.INFO));
-      expect(b.level, equals(Level.INFO));
-      expect(c.level, equals(Level.INFO));
-
-      root.level = Level.SHOUT;
-      b.level = Level.FINE;
-
-      expect(root.level, equals(Level.SHOUT));
-      expect(a.level, equals(Level.SHOUT));
-      expect(b.level, equals(Level.FINE));
-      expect(c.level, equals(Level.FINE));
-    });
-
-    test('isLoggable is appropriate', () {
-      hierarchicalLoggingEnabled = true;
-      root.level = Level.SEVERE;
-      c.level = Level.ALL;
-      e.level = Level.OFF;
-
-      expect(root.isLoggable(Level.SHOUT), isTrue);
-      expect(root.isLoggable(Level.SEVERE), isTrue);
-      expect(root.isLoggable(Level.WARNING), isFalse);
-      expect(c.isLoggable(Level.FINEST), isTrue);
-      expect(c.isLoggable(Level.FINE), isTrue);
-      expect(!e.isLoggable(Level.SHOUT), isTrue);
-    });
-
-    test('add/remove handlers - no hierarchy', () {
-      int calls = 0;
-      var handler = (_) { calls++; };
-      c.on.record.add(handler);
-      root.info("foo");
-      root.info("foo");
-      expect(calls, equals(2));
-      c.on.record.remove(handler);
-      root.info("foo");
-      expect(calls, equals(2));
-    });
-
-    test('add/remove handlers - with hierarchy', () {
-      hierarchicalLoggingEnabled = true;
-      int calls = 0;
-      var handler = (_) { calls++; };
-      c.on.record.add(handler);
-      root.info("foo");
-      root.info("foo");
-      expect(calls, equals(0));
-    });
-
-    test('logging methods store appropriate level', () {
-      root.level = Level.ALL;
-      var rootMessages = [];
-      root.on.record.add((record) {
-        rootMessages.add('${record.level}: ${record.message}');
-      });
-
-      root.finest('1');
-      root.finer('2');
-      root.fine('3');
-      root.config('4');
-      root.info('5');
-      root.warning('6');
-      root.severe('7');
-      root.shout('8');
-
-      expect(rootMessages, equals([
-        'FINEST: 1',
-        'FINER: 2',
-        'FINE: 3',
-        'CONFIG: 4',
-        'INFO: 5',
-        'WARNING: 6',
-        'SEVERE: 7',
-        'SHOUT: 8']));
-    });
-
-    test('message logging - no hierarchy', () {
-      root.level = Level.WARNING;
-      var rootMessages = [];
-      var aMessages = [];
-      var cMessages = [];
-      c.on.record.add((record) {
-        cMessages.add('${record.level}: ${record.message}');
-      });
-      a.on.record.add((record) {
-        aMessages.add('${record.level}: ${record.message}');
-      });
-      root.on.record.add((record) {
-        rootMessages.add('${record.level}: ${record.message}');
-      });
-
-      root.info('1');
-      root.fine('2');
-      root.shout('3');
-
-      b.info('4');
-      b.severe('5');
-      b.warning('6');
-      b.fine('7');
-
-      c.fine('8');
-      c.warning('9');
-      c.shout('10');
-
-      expect(rootMessages, equals([
-            // 'INFO: 1' is not loggable
-            // 'FINE: 2' is not loggable
-            'SHOUT: 3',
-            // 'INFO: 4' is not loggable
-            'SEVERE: 5',
-            'WARNING: 6',
-            // 'FINE: 7' is not loggable
-            // 'FINE: 8' is not loggable
-            'WARNING: 9',
-            'SHOUT: 10']));
-
-      // no hierarchy means we all hear the same thing.
-      expect(aMessages, equals(rootMessages));
-      expect(cMessages, equals(rootMessages));
-    });
-
-    test('message logging - with hierarchy', () {
-      hierarchicalLoggingEnabled = true;
-
-      b.level = Level.WARNING;
-
-      var rootMessages = [];
-      var aMessages = [];
-      var cMessages = [];
-      c.on.record.add((record) {
-        cMessages.add('${record.level}: ${record.message}');
-      });
-      a.on.record.add((record) {
-        aMessages.add('${record.level}: ${record.message}');
-      });
-      root.on.record.add((record) {
-        rootMessages.add('${record.level}: ${record.message}');
-      });
-
-      root.info('1');
-      root.fine('2');
-      root.shout('3');
-
-      b.info('4');
-      b.severe('5');
-      b.warning('6');
-      b.fine('7');
-
-      c.fine('8');
-      c.warning('9');
-      c.shout('10');
-
-      expect(rootMessages, equals([
-            'INFO: 1',
-            // 'FINE: 2' is not loggable
-            'SHOUT: 3',
-            // 'INFO: 4' is not loggable
-            'SEVERE: 5',
-            'WARNING: 6',
-            // 'FINE: 7' is not loggable
-            // 'FINE: 8' is not loggable
-            'WARNING: 9',
-            'SHOUT: 10']));
-
-      expect(aMessages, equals([
-            // 1,2 and 3 are lower in the hierarchy
-            // 'INFO: 4' is not loggable
-            'SEVERE: 5',
-            'WARNING: 6',
-            // 'FINE: 7' is not loggable
-            // 'FINE: 8' is not loggable
-            'WARNING: 9',
-            'SHOUT: 10']));
-
-      expect(cMessages, equals([
-            // 1 - 7 are lower in the hierarchy
-            // 'FINE: 8' is not loggable
-            'WARNING: 9',
-            'SHOUT: 10']));
-    });
-  });
-}
diff --git a/pkg/logging/test/logging_test.dart b/pkg/logging/test/logging_test.dart
index 5102c42..1af342f 100644
--- a/pkg/logging/test/logging_test.dart
+++ b/pkg/logging/test/logging_test.dart
@@ -5,7 +5,7 @@
 
 library logging_test;
 
-import '../../../pkg/logging/lib/logging.dart';
+import 'package:logging/logging.dart';
 import 'package:unittest/unittest.dart';
 
 main() {
diff --git a/pkg/oauth2/lib/src/authorization_code_grant.dart b/pkg/oauth2/lib/src/authorization_code_grant.dart
index 342c726..900dfc5 100644
--- a/pkg/oauth2/lib/src/authorization_code_grant.dart
+++ b/pkg/oauth2/lib/src/authorization_code_grant.dart
@@ -7,8 +7,7 @@
 import 'dart:async';
 import 'dart:uri';
 
-// TODO(nweiz): This should be a "package:" import. See issue 6745.
-import '../../../../pkg/http/lib/http.dart' as http;
+import 'package:http/http.dart' as http;
 
 import 'client.dart';
 import 'authorization_exception.dart';
diff --git a/pkg/oauth2/lib/src/client.dart b/pkg/oauth2/lib/src/client.dart
index 6d4d042..afb59e4 100644
--- a/pkg/oauth2/lib/src/client.dart
+++ b/pkg/oauth2/lib/src/client.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:uri';
 
-import '../../../../pkg/http/lib/http.dart' as http;
+import 'package:http/http.dart' as http;
 
 import 'authorization_exception.dart';
 import 'credentials.dart';
diff --git a/pkg/oauth2/lib/src/credentials.dart b/pkg/oauth2/lib/src/credentials.dart
index bd9ab04..420dc49 100644
--- a/pkg/oauth2/lib/src/credentials.dart
+++ b/pkg/oauth2/lib/src/credentials.dart
@@ -8,7 +8,8 @@
 import 'dart:json' as JSON;
 import 'dart:uri';
 
-import '../../../../pkg/http/lib/http.dart' as http;
+import 'package:http/http.dart' as http;
+
 import 'handle_access_token_response.dart';
 import 'utils.dart';
 
diff --git a/pkg/oauth2/lib/src/handle_access_token_response.dart b/pkg/oauth2/lib/src/handle_access_token_response.dart
index 9f9e867..65e706e 100644
--- a/pkg/oauth2/lib/src/handle_access_token_response.dart
+++ b/pkg/oauth2/lib/src/handle_access_token_response.dart
@@ -8,7 +8,7 @@
 import 'dart:json' as JSON;
 import 'dart:uri';
 
-import '../../../../pkg/http/lib/http.dart' as http;
+import 'package:http/http.dart' as http;
 
 import 'credentials.dart';
 import 'authorization_exception.dart';
diff --git a/pkg/oauth2/test/authorization_code_grant_test.dart b/pkg/oauth2/test/authorization_code_grant_test.dart
index ad784a5..85c055b 100644
--- a/pkg/oauth2/test/authorization_code_grant_test.dart
+++ b/pkg/oauth2/test/authorization_code_grant_test.dart
@@ -9,10 +9,11 @@
 import 'dart:json' as JSON;
 import 'dart:uri';
 
-import '../../../pkg/unittest/lib/unittest.dart';
-import '../../../pkg/http/lib/http.dart' as http;
-import '../../../pkg/http/lib/testing.dart';
-import '../lib/oauth2.dart' as oauth2;
+import 'package:unittest/unittest.dart';
+import 'package:http/http.dart' as http;
+import 'package:http/testing.dart';
+import 'package:oauth2/oauth2.dart' as oauth2;
+
 import 'utils.dart';
 
 final redirectUrl = Uri.parse('http://example.com/redirect');
diff --git a/pkg/oauth2/test/client_test.dart b/pkg/oauth2/test/client_test.dart
index a815a22..7049122 100644
--- a/pkg/oauth2/test/client_test.dart
+++ b/pkg/oauth2/test/client_test.dart
@@ -9,9 +9,10 @@
 import 'dart:json' as JSON;
 import 'dart:uri';
 
-import '../../../pkg/unittest/lib/unittest.dart';
-import '../../../pkg/http/lib/http.dart' as http;
-import '../lib/oauth2.dart' as oauth2;
+import 'package:http/http.dart' as http;
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:unittest/unittest.dart';
+
 import 'utils.dart';
 
 final Uri requestUri = Uri.parse("http://example.com/resource");
diff --git a/pkg/oauth2/test/credentials_test.dart b/pkg/oauth2/test/credentials_test.dart
index e21b301..8e40a4a 100644
--- a/pkg/oauth2/test/credentials_test.dart
+++ b/pkg/oauth2/test/credentials_test.dart
@@ -9,9 +9,10 @@
 import 'dart:json' as JSON;
 import 'dart:uri';
 
-import '../../../pkg/unittest/lib/unittest.dart';
-import '../../../pkg/http/lib/http.dart' as http;
-import '../lib/oauth2.dart' as oauth2;
+import 'package:http/http.dart' as http;
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:unittest/unittest.dart';
+
 import 'utils.dart';
 
 final Uri tokenEndpoint = Uri.parse('http://example.com/token');
diff --git a/pkg/oauth2/test/handle_access_token_response_test.dart b/pkg/oauth2/test/handle_access_token_response_test.dart
index e39ee56..772f263 100644
--- a/pkg/oauth2/test/handle_access_token_response_test.dart
+++ b/pkg/oauth2/test/handle_access_token_response_test.dart
@@ -8,10 +8,11 @@
 import 'dart:json' as JSON;
 import 'dart:uri';
 
-import '../../../pkg/unittest/lib/unittest.dart';
-import '../../../pkg/http/lib/http.dart' as http;
-import '../lib/oauth2.dart' as oauth2;
-import '../lib/src/handle_access_token_response.dart';
+import 'package:http/http.dart' as http;
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:oauth2/src/handle_access_token_response.dart';
+import 'package:unittest/unittest.dart';
+
 import 'utils.dart';
 
 final Uri tokenEndpoint = Uri.parse("https://example.com/token");
diff --git a/pkg/oauth2/test/utils.dart b/pkg/oauth2/test/utils.dart
index 04b194e..b874cc4 100644
--- a/pkg/oauth2/test/utils.dart
+++ b/pkg/oauth2/test/utils.dart
@@ -7,10 +7,10 @@
 import 'dart:async';
 import 'dart:collection' show Queue;
 
-import '../../../pkg/unittest/lib/unittest.dart';
-import '../../../pkg/http/lib/http.dart' as http;
-import '../../../pkg/http/lib/testing.dart';
-import '../lib/oauth2.dart' as oauth2;
+import 'package:http/http.dart' as http;
+import 'package:http/testing.dart';
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:unittest/unittest.dart';
 
 class ExpectClient extends MockClient {
   final Queue<MockClientHandler> _handlers;
diff --git a/pkg/oauth2/test/utils_test.dart b/pkg/oauth2/test/utils_test.dart
index 2fa4b73..145e99b 100644
--- a/pkg/oauth2/test/utils_test.dart
+++ b/pkg/oauth2/test/utils_test.dart
@@ -4,9 +4,8 @@
 
 library utils_test;
 
-import '../../../pkg/unittest/lib/unittest.dart';
-import '../lib/src/utils.dart';
-
+import 'package:oauth2/src/utils.dart';
+import 'package:unittest/unittest.dart';
 
 void main() {
   group('AuthenticateHeader', () {
diff --git a/pkg/pkg.status b/pkg/pkg.status
index b90eaa1..0affdd6 100644
--- a/pkg/pkg.status
+++ b/pkg/pkg.status
@@ -37,6 +37,11 @@
 # Issue 8440 forces us to use pathos in the scheduled_test tests, which would
 # otherwise be dart2js-compatible.
 scheduled_test/test/*: Skip
+
+# We use pathos in the stack_trace tests. We can run them on dart2js when issue
+# 6943 is fixed.
+stack_trace/test/*: Skip
+
 source_maps/test/vlq_test: Fail # A VLQ test checks for large numbers that
                                 # overflow in JS (numbers slightly larger than
                                 # 32 bits where we do bitwise operations).
@@ -61,6 +66,10 @@
 # otherwise be dart2js-compatible.
 scheduled_test/test/*: Skip
 
+# We use pathos in the stack_trace tests. We can run them on dart2js when issue
+# 6943 is fixed.
+stack_trace/test/*: Skip
+
 [ $runtime == opera && $compiler == dart2js ]
 intl/test/find_default_locale_browser_test: Fail
 intl/test/date_time_format_http_request_test: Skip # Timeout.
diff --git a/pkg/scheduled_test/lib/descriptor.dart b/pkg/scheduled_test/lib/descriptor.dart
index f832b9a..ecb89f3 100644
--- a/pkg/scheduled_test/lib/descriptor.dart
+++ b/pkg/scheduled_test/lib/descriptor.dart
@@ -64,7 +64,7 @@
 
 import 'dart:async';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import 'scheduled_test.dart';
 import 'src/descriptor/async_descriptor.dart';
diff --git a/pkg/scheduled_test/lib/scheduled_test.dart b/pkg/scheduled_test/lib/scheduled_test.dart
index 8451e18..4c4eed1 100644
--- a/pkg/scheduled_test/lib/scheduled_test.dart
+++ b/pkg/scheduled_test/lib/scheduled_test.dart
@@ -175,14 +175,14 @@
 
 import 'dart:async';
 
-import '../../../pkg/unittest/lib/unittest.dart' as unittest;
+import 'package:unittest/unittest.dart' as unittest;
 
 import 'src/schedule.dart';
 import 'src/schedule_error.dart';
 import 'src/utils.dart';
 
-export '../../../pkg/unittest/lib/matcher.dart' hide completes, completion;
-export '../../../pkg/unittest/lib/unittest.dart' show
+export 'package:unittest/matcher.dart' hide completes, completion;
+export 'package:unittest/unittest.dart' show
     config, configure, Configuration, logMessage, expectThrow;
 
 export 'src/schedule.dart';
diff --git a/pkg/scheduled_test/lib/src/descriptor/directory_descriptor.dart b/pkg/scheduled_test/lib/src/descriptor/directory_descriptor.dart
index 690f92f..feaa55b 100644
--- a/pkg/scheduled_test/lib/src/descriptor/directory_descriptor.dart
+++ b/pkg/scheduled_test/lib/src/descriptor/directory_descriptor.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../../descriptor.dart';
 import '../../scheduled_test.dart';
diff --git a/pkg/scheduled_test/lib/src/descriptor/file_descriptor.dart b/pkg/scheduled_test/lib/src/descriptor/file_descriptor.dart
index ffcf567..75327d1 100644
--- a/pkg/scheduled_test/lib/src/descriptor/file_descriptor.dart
+++ b/pkg/scheduled_test/lib/src/descriptor/file_descriptor.dart
@@ -9,7 +9,7 @@
 import 'dart:math' as math;
 import 'dart:utf';
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../../descriptor.dart';
 import '../../scheduled_test.dart';
diff --git a/pkg/scheduled_test/lib/src/descriptor/nothing_descriptor.dart b/pkg/scheduled_test/lib/src/descriptor/nothing_descriptor.dart
index 00fa706..39f61cb 100644
--- a/pkg/scheduled_test/lib/src/descriptor/nothing_descriptor.dart
+++ b/pkg/scheduled_test/lib/src/descriptor/nothing_descriptor.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../../descriptor.dart';
 import '../../scheduled_test.dart';
diff --git a/pkg/scheduled_test/lib/src/descriptor/pattern_descriptor.dart b/pkg/scheduled_test/lib/src/descriptor/pattern_descriptor.dart
index 1cea5f5..3735f82 100644
--- a/pkg/scheduled_test/lib/src/descriptor/pattern_descriptor.dart
+++ b/pkg/scheduled_test/lib/src/descriptor/pattern_descriptor.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../../descriptor.dart';
 import '../../scheduled_test.dart';
diff --git a/pkg/scheduled_test/lib/src/schedule.dart b/pkg/scheduled_test/lib/src/schedule.dart
index 977fc3f7..42c6fa2 100644
--- a/pkg/scheduled_test/lib/src/schedule.dart
+++ b/pkg/scheduled_test/lib/src/schedule.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:collection';
 
-import '../../../../pkg/unittest/lib/unittest.dart' as unittest;
+import 'package:unittest/unittest.dart' as unittest;
 
 import 'mock_clock.dart' as mock_clock;
 import 'schedule_error.dart';
diff --git a/pkg/scheduled_test/test/descriptor_test.dart b/pkg/scheduled_test/test/descriptor_test.dart
index ff0efe5..baca328 100644
--- a/pkg/scheduled_test/test/descriptor_test.dart
+++ b/pkg/scheduled_test/test/descriptor_test.dart
@@ -7,9 +7,9 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
-import '../lib/descriptor.dart' as d;
-import '../lib/scheduled_test.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/descriptor.dart' as d;
+import 'package:scheduled_test/scheduled_test.dart';
 
 import 'metatest.dart';
 import 'utils.dart';
diff --git a/pkg/scheduled_test/test/metatest.dart b/pkg/scheduled_test/test/metatest.dart
index 657e93e..0771ff4 100644
--- a/pkg/scheduled_test/test/metatest.dart
+++ b/pkg/scheduled_test/test/metatest.dart
@@ -13,8 +13,8 @@
 import 'dart:async';
 import 'dart:isolate';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
-import '../../../pkg/unittest/lib/unittest.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:unittest/unittest.dart';
 
 import 'utils.dart';
 
@@ -184,9 +184,11 @@
 
 /// Ensure that the metatest configuration is loaded.
 void _ensureInitialized() {
-  if (config is! _MetaConfiguration) configure(new _MetaConfiguration());
+  unittestConfiguration = _singleton;
 }
 
+final _singleton = new _MetaConfiguration();
+
 /// Special test configuration for use within the child isolates. This hides all
 /// output and reports data back to the parent isolate.
 class _MetaConfiguration extends Configuration {
diff --git a/pkg/scheduled_test/test/scheduled_process_test.dart b/pkg/scheduled_test/test/scheduled_process_test.dart
index 66b288f..9742947 100644
--- a/pkg/scheduled_test/test/scheduled_process_test.dart
+++ b/pkg/scheduled_test/test/scheduled_process_test.dart
@@ -7,10 +7,10 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
-import '../lib/scheduled_process.dart';
-import '../lib/scheduled_test.dart';
-import '../lib/src/mock_clock.dart' as mock_clock;
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_process.dart';
+import 'package:scheduled_test/scheduled_test.dart';
+import 'package:scheduled_test/src/mock_clock.dart' as mock_clock;
 
 import 'metatest.dart';
 import 'utils.dart';
diff --git a/pkg/scheduled_test/test/scheduled_server_test.dart b/pkg/scheduled_test/test/scheduled_server_test.dart
index aeb654f..19135e0 100644
--- a/pkg/scheduled_test/test/scheduled_server_test.dart
+++ b/pkg/scheduled_test/test/scheduled_server_test.dart
@@ -7,10 +7,10 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../../../pkg/http/lib/http.dart' as http;
-import '../lib/scheduled_server.dart';
-import '../lib/scheduled_test.dart';
-import '../lib/src/mock_clock.dart' as mock_clock;
+import 'package:http/http.dart' as http;
+import 'package:scheduled_test/scheduled_server.dart';
+import 'package:scheduled_test/scheduled_test.dart';
+import 'package:scheduled_test/src/mock_clock.dart' as mock_clock;
 
 import 'metatest.dart';
 import 'utils.dart';
diff --git a/pkg/scheduled_test/test/scheduled_test_test.dart b/pkg/scheduled_test/test/scheduled_test_test.dart
index e42f810..b3c8477 100644
--- a/pkg/scheduled_test/test/scheduled_test_test.dart
+++ b/pkg/scheduled_test/test/scheduled_test_test.dart
@@ -6,8 +6,8 @@
 
 import 'dart:async';
 
-import '../lib/scheduled_test.dart';
-import '../lib/src/mock_clock.dart' as mock_clock;
+import 'package:scheduled_test/scheduled_test.dart';
+import 'package:scheduled_test/src/mock_clock.dart' as mock_clock;
 
 import 'metatest.dart';
 import 'utils.dart';
diff --git a/pkg/scheduled_test/test/substitute_future_test.dart b/pkg/scheduled_test/test/substitute_future_test.dart
index be42ccc..f9c8b32 100644
--- a/pkg/scheduled_test/test/substitute_future_test.dart
+++ b/pkg/scheduled_test/test/substitute_future_test.dart
@@ -6,8 +6,8 @@
 
 import 'dart:async';
 
-import '../lib/src/substitute_future.dart';
-import '../../../pkg/unittest/lib/unittest.dart';
+import 'package:scheduled_test/src/substitute_future.dart';
+import 'package:unittest/unittest.dart';
 
 void main() {
   group('with no substitution, works like a normal Future for', () {
diff --git a/pkg/scheduled_test/test/utils.dart b/pkg/scheduled_test/test/utils.dart
index 7750e8a..d6c272d4 100644
--- a/pkg/scheduled_test/test/utils.dart
+++ b/pkg/scheduled_test/test/utils.dart
@@ -7,10 +7,10 @@
 import 'dart:io';
 import 'dart:async';
 
-import '../lib/src/utils.dart';
-import '../lib/src/mock_clock.dart' as mock_clock;
+import 'package:scheduled_test/src/utils.dart';
+import 'package:scheduled_test/src/mock_clock.dart' as mock_clock;
 
-export '../lib/src/utils.dart';
+export 'package:scheduled_test/src/utils.dart';
 
 /// Wraps [input] to provide a timeout. If [input] completes before
 /// [milliseconds] have passed, then the return value completes in the same way.
diff --git a/pkg/scheduled_test/test/value_future_test.dart b/pkg/scheduled_test/test/value_future_test.dart
index ebbcf17..a5777b3 100644
--- a/pkg/scheduled_test/test/value_future_test.dart
+++ b/pkg/scheduled_test/test/value_future_test.dart
@@ -6,8 +6,8 @@
 
 import 'dart:async';
 
-import '../lib/src/value_future.dart';
-import '../../../pkg/unittest/lib/unittest.dart';
+import 'package:scheduled_test/src/value_future.dart';
+import 'package:unittest/unittest.dart';
 
 void main() {
   group('works like a normal Future for', () {
diff --git a/pkg/stack_trace/README.md b/pkg/stack_trace/README.md
new file mode 100644
index 0000000..6a8112a
--- /dev/null
+++ b/pkg/stack_trace/README.md
@@ -0,0 +1,57 @@
+This library provides the ability to parse, inspect, and manipulate stack traces
+produced by the underlying Dart implementation. It also provides functions to
+produce string representations of stack traces in a more readable format than
+the native [StackTrace] implementation.
+
+`Trace`s can be parsed from native [StackTrace]s using `Trace.from`, or captured
+using `Trace.current`. Native [StackTrace]s can also be directly converted to
+human-readable strings using `Trace.format`.
+
+[StackTrace]: http://api.dartlang.org/docs/releases/latest/dart_core/StackTrace.html
+
+Here's an example native stack trace from debugging this library:
+
+    #0      Object.noSuchMethod (dart:core-patch:1884:25)
+    #1      Trace.terse.<anonymous closure> (file:///usr/local/google-old/home/goog/dart/dart/pkg/stack_trace/lib/src/trace.dart:47:21)
+    #2      IterableMixinWorkaround.reduce (dart:collection:29:29)
+    #3      List.reduce (dart:core-patch:1247:42)
+    #4      Trace.terse (file:///usr/local/google-old/home/goog/dart/dart/pkg/stack_trace/lib/src/trace.dart:40:35)
+    #5      format (file:///usr/local/google-old/home/goog/dart/dart/pkg/stack_trace/lib/stack_trace.dart:24:28)
+    #6      main.<anonymous closure> (file:///usr/local/google-old/home/goog/dart/dart/test.dart:21:29)
+    #7      _CatchErrorFuture._sendError (dart:async:525:24)
+    #8      _FutureImpl._setErrorWithoutAsyncTrace (dart:async:393:26)
+    #9      _FutureImpl._setError (dart:async:378:31)
+    #10     _ThenFuture._sendValue (dart:async:490:16)
+    #11     _FutureImpl._handleValue.<anonymous closure> (dart:async:349:28)
+    #12     Timer.run.<anonymous closure> (dart:async:2402:21)
+    #13     Timer.Timer.<anonymous closure> (dart:async-patch:15:15)
+
+and its human-readable representation:
+
+    dart:core-patch                             Object.noSuchMethod
+    pkg/stack_trace/lib/src/trace.dart 47:21    Trace.terse.<fn>
+    dart:collection                             IterableMixinWorkaround.reduce
+    dart:core-patch                             List.reduce
+    pkg/stack_trace/lib/src/trace.dart 40:35    Trace.terse
+    pkg/stack_trace/lib/stack_trace.dart 24:28  format
+    test.dart 21:29                             main.<fn>
+    dart:async                                  _CatchErrorFuture._sendError
+    dart:async                                  _FutureImpl._setErrorWithoutAsyncTrace
+    dart:async                                  _FutureImpl._setError
+    dart:async                                  _ThenFuture._sendValue
+    dart:async                                  _FutureImpl._handleValue.<fn>
+    dart:async                                  Timer.run.<fn>
+    dart:async-patch                            Timer.Timer.<fn>
+
+You can further clean up the stack trace using `Trace.terse`. This folds
+together multiple stack frames from the Dart core libraries, so that only the
+core library method that was directly called from user code is visible. For
+example:
+
+    dart:core                                   Object.noSuchMethod
+    pkg/stack_trace/lib/src/trace.dart 47:21    Trace.terse.<fn>
+    dart:core                                   List.reduce
+    pkg/stack_trace/lib/src/trace.dart 40:35    Trace.terse
+    pkg/stack_trace/lib/stack_trace.dart 24:28  format
+    test.dart 21:29                             main.<fn>
+    dart:async                                  Timer.Timer.<fn>
diff --git a/pkg/stack_trace/lib/src/frame.dart b/pkg/stack_trace/lib/src/frame.dart
new file mode 100644
index 0000000..fdf4fe0
--- /dev/null
+++ b/pkg/stack_trace/lib/src/frame.dart
@@ -0,0 +1,88 @@
+// Copyright (c) 2013, 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 frame;
+
+import 'dart:uri';
+
+import 'package:pathos/path.dart' as path;
+
+import 'trace.dart';
+
+final _nativeFrameRegExp = new RegExp(
+    r'^#\d+\s+([^\s].*) \((.+):(\d+):(\d+)\)$');
+
+/// A single stack frame. Each frame points to a precise location in Dart code.
+class Frame {
+  /// The URI of the file in which the code is located.
+  ///
+  /// This URI will usually have the scheme `dart`, `file`, `http`, or `https`.
+  final Uri uri;
+
+  /// The line number on which the code location is located.
+  final int line;
+
+  /// The column number of the code location.
+  final int column;
+
+  /// The name of the member in which the code location occurs.
+  ///
+  /// Anonymous closures are represented as `<fn>` in this member string.
+  final String member;
+
+  /// Whether this stack frame comes from the Dart core libraries.
+  bool get isCore => uri.scheme == 'dart';
+
+  /// Returns a human-friendly description of the library that this stack frame
+  /// comes from.
+  ///
+  /// This will usually be the string form of [uri], but a relative path will be
+  /// used if possible.
+  String get library {
+    // TODO(nweiz): handle relative URIs here as well once pathos supports that.
+    if (uri.scheme != 'file') return uri.toString();
+    return path.relative(uri.path);
+  }
+
+  /// A human-friendly description of the code location.
+  ///
+  /// For Dart core libraries, this will omit the line and column information,
+  /// since those are useless for baked-in libraries.
+  String get location {
+    if (isCore) return library;
+    return '$library $line:$column';
+  }
+
+  /// Returns a single frame of the current stack.
+  ///
+  /// By default, this will return the frame above the current method. If
+  /// [level] is `0`, it will return the current method's frame; if [level] is
+  /// higher than `1`, it will return higher frames.
+  factory Frame.caller([int level=1]) {
+    if (level < 0) {
+      throw new ArgumentError("Argument [level] must be greater than or equal "
+          "to 0.");
+    }
+
+    return new Trace.current(level + 1).frames.first;
+  }
+
+  /// Parses a string representation of a stack frame.
+  ///
+  /// [frame] should be formatted in the same way as a native stack trace frame.
+  factory Frame.parse(String frame) {
+    var match = _nativeFrameRegExp.firstMatch(frame);
+    if (match == null) {
+      throw new FormatException("Couldn't parse stack trace line '$frame'.");
+    }
+
+    var uri = new Uri.fromString(match[2]);
+    var member = match[1].replaceAll("<anonymous closure>", "<fn>");
+    return new Frame(uri, int.parse(match[3]), int.parse(match[4]), member);
+  }
+
+  Frame(this.uri, this.line, this.column, this.member);
+
+  String toString() => '$location in $member';
+}
diff --git a/pkg/stack_trace/lib/src/trace.dart b/pkg/stack_trace/lib/src/trace.dart
new file mode 100644
index 0000000..1ab7695
--- /dev/null
+++ b/pkg/stack_trace/lib/src/trace.dart
@@ -0,0 +1,127 @@
+// Copyright (c) 2013, 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 trace;
+
+import 'dart:uri';
+
+import 'frame.dart';
+
+final _patchRegExp = new RegExp(r"-patch$");
+
+/// A stack trace, comprised of a list of stack frames.
+class Trace implements StackTrace {
+  // TODO(nweiz): make this read-only once issue 8321 is fixed.
+  /// The stack frames that comprise this stack trace.
+  final List<Frame> frames;
+
+  /// Returns a human-readable representation of [stackTrace]. If [terse] is
+  /// set, this folds together multiple stack frames from the Dart core
+  /// libraries, so that only the core library method directly called from user
+  /// code is visible (see [Trace.terse]).
+  static String format(StackTrace stackTrace, {bool terse: true}) {
+    var trace = new Trace.from(stackTrace);
+    if (terse) trace = trace.terse;
+    return trace.toString();
+  }
+
+  /// Returns the current stack trace.
+  ///
+  /// By default, the first frame of this trace will be the line where
+  /// [Trace.current] is called. If [level] is passed, the trace will start that
+  /// many frames up instead.
+  factory Trace.current([int level=0]) {
+    if (level < 0) {
+      throw new ArgumentError("Argument [level] must be greater than or equal "
+          "to 0.");
+    }
+
+    try {
+      throw '';
+    } catch (_, nativeTrace) {
+      var trace = new Trace.from(nativeTrace);
+      return new Trace(trace.frames.skip(level + 1));
+    }
+  }
+
+  /// Returns a new stack trace containing the same data as [trace].
+  ///
+  /// If [trace] is a native [StackTrace], its data will be parsed out; if it's
+  /// a [Trace], it will be returned as-is.
+  factory Trace.from(StackTrace trace) {
+    if (trace is Trace) return trace;
+    return new Trace.parse(trace.fullStackTrace);
+  }
+
+  /// Parses a string representation of a stack trace.
+  ///
+  /// [trace] should be formatted in the same way as native stack traces.
+  Trace.parse(String trace)
+      : this(trace.trim().split("\n").map((line) => new Frame.parse(line)));
+
+  /// Returns a new [Trace] comprised of [frames].
+  Trace(Iterable<Frame> frames)
+      : frames = frames.toList();
+
+  // TODO(nweiz): Keep track of which [Frame]s are part of the partial stack
+  // trace and only print them.
+  /// Returns a string representation of this stack trace.
+  ///
+  /// This is identical to [toString]. It will not be formatted in the manner of
+  /// native stack traces.
+  String get stackTrace => toString();
+
+  /// Returns a string representation of this stack trace.
+  ///
+  /// This is identical to [toString]. It will not be formatted in the manner of
+  /// native stack traces.
+  String get fullStackTrace => toString();
+
+  /// Returns a terser version of [this]. This is accomplished by folding
+  /// together multiple stack frames from the core library. If multiple such
+  /// frames appear in a row, only the last (the one directly called by user
+  /// code) is kept. Core library patches are also renamed to remove their
+  /// `-patch` suffix.
+  Trace get terse {
+    var newFrames = <Frame>[];
+    for (var frame in frames.reversed) {
+      if (!frame.isCore) {
+        newFrames.add(frame);
+      } else if (newFrames.isEmpty || !newFrames.last.isCore) {
+        var library = frame.library.replaceAll(_patchRegExp, '');
+        newFrames.add(new Frame(
+            Uri.parse(library), frame.line, frame.column, frame.member));
+      }
+    }
+
+    return new Trace(newFrames.reversed);
+  }
+
+  /// Returns a human-readable string representation of [this].
+  String toString() {
+    if (frames.length == '') return '';
+
+    // Figure out the longest path so we know how much to pad.
+    var longest = frames.map((frame) => frame.location.length).max();
+
+    // Print out the stack trace nicely formatted.
+    return frames.map((frame) {
+      return '${_padRight(frame.location, longest)}  ${frame.member}\n';
+    }).join();
+  }
+}
+
+/// Returns [string] with enough spaces added to the end to make it [length]
+/// characters long.
+String _padRight(String string, int length) {
+  if (string.length >= length) return string;
+
+  var result = new StringBuffer();
+  result.write(string);
+  for (var i = 0; i < length - string.length; i++) {
+    result.write(' ');
+  }
+
+  return result.toString();
+}
diff --git a/pkg/stack_trace/lib/stack_trace.dart b/pkg/stack_trace/lib/stack_trace.dart
new file mode 100644
index 0000000..455dd57
--- /dev/null
+++ b/pkg/stack_trace/lib/stack_trace.dart
@@ -0,0 +1,11 @@
+// Copyright (c) 2013, 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 stack_trace;
+
+import 'src/trace.dart';
+import 'src/frame.dart';
+
+export 'src/trace.dart';
+export 'src/frame.dart';
diff --git a/pkg/stack_trace/pubspec.yaml b/pkg/stack_trace/pubspec.yaml
new file mode 100644
index 0000000..3a679a8
--- /dev/null
+++ b/pkg/stack_trace/pubspec.yaml
@@ -0,0 +1,11 @@
+name: stack_trace
+author: "Dart Team <misc@dartlang.org>"
+homepage: http://www.dartlang.org
+description: >
+  A package for manipulating stack traces and printing them readably.
+
+dependencies:
+  pathos: any
+
+dev_dependencies:
+  unittest: any
diff --git a/pkg/stack_trace/test/frame_test.dart b/pkg/stack_trace/test/frame_test.dart
new file mode 100644
index 0000000..5c5a32e
--- /dev/null
+++ b/pkg/stack_trace/test/frame_test.dart
@@ -0,0 +1,166 @@
+// Copyright (c) 2013, 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 frame_test;
+
+import 'dart:io';
+import 'dart:uri';
+
+import 'package:pathos/path.dart' as path;
+import 'package:stack_trace/stack_trace.dart';
+import 'package:unittest/unittest.dart';
+
+String getStackFrame() {
+  try {
+    throw '';
+  } catch (_, stackTrace) {
+    return stackTrace.toString().split("\n").first;
+  }
+}
+
+Frame getCaller([int level]) {
+  if (level == null) return new Frame.caller();
+  return new Frame.caller(level);
+}
+
+Frame nestedGetCaller(int level) => getCaller(level);
+
+void main() {
+  test('parses a stack frame correctly', () {
+    var frame = new Frame.parse("#1      Foo._bar "
+        "(file:///home/nweiz/code/stuff.dart:42:21)");
+    expect(frame.uri,
+        equals(new Uri.fromString("file:///home/nweiz/code/stuff.dart")));
+    expect(frame.line, equals(42));
+    expect(frame.column, equals(21));
+    expect(frame.member, equals('Foo._bar'));
+  });
+
+  test('parses a real stack frame correctly', () {
+    var frame = new Frame.parse(getStackFrame());
+    // TODO(nweiz): use URL-style paths when such a thing exists.
+    var builder = new path.Builder(style: path.Style.posix);
+    expect(builder.basename(frame.uri.path), equals('frame_test.dart'));
+    expect(frame.line, equals(16));
+    expect(frame.column, equals(5));
+    expect(frame.member, equals('getStackFrame'));
+  });
+
+  test('converts "<anonymous closure>" to "<fn>"', () {
+    String parsedMember(String member) =>
+        new Frame.parse('#0 $member (foo:0:0)').member;
+
+    expect(parsedMember('Foo.<anonymous closure>'), equals('Foo.<fn>'));
+    expect(parsedMember('<anonymous closure>.<anonymous closure>.bar'),
+        equals('<fn>.<fn>.bar'));
+  });
+
+  test('throws a FormatException for malformed frames', () {
+    expect(() => new Frame.parse(''), throwsFormatException);
+    expect(() => new Frame.parse('#1'), throwsFormatException);
+    expect(() => new Frame.parse('#1      Foo'), throwsFormatException);
+    expect(() => new Frame.parse('#1      Foo (dart:async)'),
+        throwsFormatException);
+    expect(() => new Frame.parse('#1      Foo (dart:async:10)'),
+        throwsFormatException);
+    expect(() => new Frame.parse('#1      (dart:async:10:15)'),
+        throwsFormatException);
+    expect(() => new Frame.parse('Foo (dart:async:10:15)'),
+        throwsFormatException);
+  });
+
+  test('only considers dart URIs to be core', () {
+    bool isCore(String library) =>
+      new Frame.parse('#0 Foo ($library:0:0)').isCore;
+
+    expect(isCore('dart:core'), isTrue);
+    expect(isCore('dart:async'), isTrue);
+    expect(isCore('bart:core'), isFalse);
+    expect(isCore('sdart:core'), isFalse);
+    expect(isCore('darty:core'), isFalse);
+  });
+
+  group('.caller()', () {
+    test('with no argument returns the parent frame', () {
+      expect(getCaller().member, equals('main.<fn>.<fn>'));
+    });
+
+    test('at level 0 returns the current frame', () {
+      expect(getCaller(0).member, equals('getCaller'));
+    });
+
+    test('at level 1 returns the current frame', () {
+      expect(getCaller(1).member, equals('main.<fn>.<fn>'));
+    });
+
+    test('at level 2 returns the grandparent frame', () {
+      expect(nestedGetCaller(2).member, equals('main.<fn>.<fn>'));
+    });
+
+    test('throws an ArgumentError for negative levels', () {
+      expect(() => new Frame.caller(-1), throwsArgumentError);
+    });
+  });
+
+  group('.library', () {
+    test('returns the URI string for non-file URIs', () {
+      expect(new Frame.parse('#0 Foo (dart:async:0:0)').library,
+          equals('dart:async'));
+      expect(new Frame.parse('#0 Foo '
+              '(http://dartlang.org/stuff/thing.dart:0:0)').library,
+          equals('http://dartlang.org/stuff/thing.dart'));
+    });
+
+    test('returns the relative path for file URIs', () {
+      var uri = _pathToFileUri(path.join('foo', 'bar.dart'));
+      expect(new Frame.parse('#0 Foo ($uri:0:0)').library,
+          equals(path.join('foo', 'bar.dart')));
+    });
+  });
+
+  group('.location', () {
+    test('returns the library and line/column numbers for non-core '
+        'libraries', () {
+      expect(new Frame.parse('#0 Foo '
+              '(http://dartlang.org/thing.dart:5:10)').location,
+          equals('http://dartlang.org/thing.dart 5:10'));
+      var uri = _pathToFileUri(path.join('foo', 'bar.dart'));
+      expect(new Frame.parse('#0 Foo ($uri:1:2)').location,
+          equals('${path.join('foo', 'bar.dart')} 1:2'));
+    });
+
+    test('just returns the library for core libraries', () {
+      expect(new Frame.parse('#0 Foo (dart:core:5:10)').location,
+          equals('dart:core'));
+      expect(new Frame.parse('#0 Foo (dart:async-patch:1:2)').location,
+          equals('dart:async-patch'));
+    });
+  });
+
+  group('.toString()', () {
+    test('returns the library and line/column numbers for non-core '
+        'libraries', () {
+      expect(new Frame.parse('#0 Foo (http://dartlang.org/thing.dart:5:10)')
+              .toString(),
+          equals('http://dartlang.org/thing.dart 5:10 in Foo'));
+    });
+
+    test('just returns the library for core libraries', () {
+      expect(new Frame.parse('#0 Foo (dart:core:5:10)').toString(),
+          equals('dart:core in Foo'));
+    });
+
+    test('converts "<anonymous closure>" to "<fn>"', () {
+      expect(new Frame.parse('#0 Foo.<anonymous closure> (dart:core:5:10)')
+              .toString(),
+          equals('dart:core in Foo.<fn>'));
+    });
+  });
+}
+
+String _pathToFileUri(String pathString) {
+  pathString = path.absolute(pathString);
+  if (Platform.operatingSystem != 'windows') return 'file://$pathString';
+  return 'file:///${pathString.replaceAll("\\", "/")}';
+}
diff --git a/pkg/stack_trace/test/trace_test.dart b/pkg/stack_trace/test/trace_test.dart
new file mode 100644
index 0000000..2cbe48d
--- /dev/null
+++ b/pkg/stack_trace/test/trace_test.dart
@@ -0,0 +1,141 @@
+// Copyright (c) 2013, 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 trace_test;
+
+import 'dart:io';
+import 'dart:uri';
+
+import 'package:pathos/path.dart' as path;
+import 'package:stack_trace/stack_trace.dart';
+import 'package:unittest/unittest.dart';
+
+String getStackTraceString() {
+  try {
+    throw '';
+  } catch (_, stackTrace) {
+    return stackTrace.toString();
+  }
+}
+
+StackTrace getStackTraceObject() {
+  try {
+    throw '';
+  } catch (_, stackTrace) {
+    return stackTrace;
+  }
+}
+
+Trace getCurrentTrace([int level]) => new Trace.current(level);
+
+Trace nestedGetCurrentTrace(int level) => getCurrentTrace(level);
+
+void main() {
+  test('parses a stack trace correctly', () {
+    var trace = new Trace.parse('''
+#0      Foo._bar (file:///home/nweiz/code/stuff.dart:42:21)
+#1      zip.<anonymous closure>.zap (dart:async:0:2)
+#2      zip.<anonymous closure>.zap (http://pub.dartlang.org/thing.dart:1:100)
+''');
+
+    expect(trace.frames[0].uri,
+        equals(new Uri.fromString("file:///home/nweiz/code/stuff.dart")));
+    expect(trace.frames[1].uri, equals(new Uri.fromString("dart:async")));
+    expect(trace.frames[2].uri,
+        equals(new Uri.fromString("http://pub.dartlang.org/thing.dart")));
+  });
+
+  test('parses a real stack trace correctly', () {
+    var trace = new Trace.parse(getStackTraceString());
+    // TODO(nweiz): use URL-style paths when such a thing exists.
+    var builder = new path.Builder(style: path.Style.posix);
+    expect(builder.basename(trace.frames.first.uri.path),
+        equals('trace_test.dart'));
+    expect(trace.frames.first.member, equals('getStackTraceString'));
+  });
+
+  test('converts from a native stack trace correctly', () {
+    var trace = new Trace.from(getStackTraceObject());
+    // TODO(nweiz): use URL-style paths when such a thing exists.
+    var builder = new path.Builder(style: path.Style.posix);
+    expect(builder.basename(trace.frames.first.uri.path),
+        equals('trace_test.dart'));
+    expect(trace.frames.first.member, equals('getStackTraceObject'));
+  });
+
+  group('.current()', () {
+    test('with no argument returns a trace starting at the current frame', () {
+      var trace = new Trace.current();
+      expect(trace.frames.first.member, equals('main.<fn>.<fn>'));
+    });
+
+    test('at level 0 returns a trace starting at the current frame', () {
+      var trace = new Trace.current(0);
+      expect(trace.frames.first.member, equals('main.<fn>.<fn>'));
+    });
+
+    test('at level 1 returns a trace starting at the parent frame', () {
+      var trace = getCurrentTrace(1);
+      expect(trace.frames.first.member, equals('main.<fn>.<fn>'));
+    });
+
+    test('at level 2 returns a trace starting at the grandparent frame', () {
+      var trace = nestedGetCurrentTrace(2);
+      expect(trace.frames.first.member, equals('main.<fn>.<fn>'));
+    });
+
+    test('throws an ArgumentError for negative levels', () {
+      expect(() => new Trace.current(-1), throwsArgumentError);
+    });
+  });
+
+  test('.toString() nicely formats the stack trace', () {
+    var uri = _pathToFileUri(path.join('foo', 'bar.dart'));
+    var trace = new Trace.parse('''
+#0      Foo._bar ($uri:42:21)
+#1      zip.<anonymous closure>.zap (dart:async:0:2)
+#2      zip.<anonymous closure>.zap (http://pub.dartlang.org/thing.dart:1:100)
+''');
+
+    expect(trace.toString(), equals('''
+${path.join('foo', 'bar.dart')} 42:21                        Foo._bar
+dart:async                                zip.<fn>.zap
+http://pub.dartlang.org/thing.dart 1:100  zip.<fn>.zap
+'''));
+  });
+
+  test('.stackTrace forwards to .toString()', () {
+    var trace = new Trace.current();
+    expect(trace.stackTrace, equals(trace.toString()));
+  });
+
+  test('.fullStackTrace forwards to .toString()', () {
+    var trace = new Trace.current();
+    expect(trace.fullStackTrace, equals(trace.toString()));
+  });
+
+  test('.terse folds core frames together bottom-up', () {
+    var trace = new Trace.parse('''
+#0 notCore (foo.dart:42:21)
+#1 top (dart:async:0:2)
+#2 bottom (dart:core:1:100)
+#3 alsoNotCore (bar.dart:10:20)
+#4 top (dart:io:5:10)
+#5 bottom (dart:async-patch:9:11)
+''');
+
+    expect(trace.terse.toString(), equals('''
+foo.dart 42:21  notCore
+dart:core       bottom
+bar.dart 10:20  alsoNotCore
+dart:async      bottom
+'''));
+  });
+}
+
+String _pathToFileUri(String pathString) {
+  pathString = path.absolute(pathString);
+  if (Platform.operatingSystem != 'windows') return 'file://$pathString';
+  return 'file:///${pathString.replaceAll("\\", "/")}';
+}
diff --git a/pkg/unittest/lib/compact_vm_config.dart b/pkg/unittest/lib/compact_vm_config.dart
index 080824a..7c4b0d6 100644
--- a/pkg/unittest/lib/compact_vm_config.dart
+++ b/pkg/unittest/lib/compact_vm_config.dart
@@ -171,6 +171,7 @@
 }
 
 void useCompactVMConfiguration() {
-  if (config != null) return;
-  configure(new CompactVMConfiguration());
+  unittestConfiguration = _singleton;
 }
+
+final _singleton = new CompactVMConfiguration();
diff --git a/pkg/unittest/lib/html_config.dart b/pkg/unittest/lib/html_config.dart
index 1b9d12a..303afb6 100644
--- a/pkg/unittest/lib/html_config.dart
+++ b/pkg/unittest/lib/html_config.dart
@@ -1,4 +1,4 @@
-// Copyright (c) 2011, the Dart project authors.  Please see the AUTHORS file
+// Copyright (c) 2013, 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.
 
@@ -164,6 +164,8 @@
 }
 
 void useHtmlConfiguration([bool isLayoutTest = false]) {
-  if (config != null) return;
-  configure(new HtmlConfiguration(isLayoutTest));
+  unittestConfiguration = isLayoutTest ? _singletonLayout : _singletonNotLayout;
 }
+
+final _singletonLayout = new HtmlConfiguration(true);
+final _singletonNotLayout = new HtmlConfiguration(false);
diff --git a/pkg/unittest/lib/html_enhanced_config.dart b/pkg/unittest/lib/html_enhanced_config.dart
index f9b9088..2fd2fa3 100644
--- a/pkg/unittest/lib/html_enhanced_config.dart
+++ b/pkg/unittest/lib/html_enhanced_config.dart
@@ -1,4 +1,4 @@
-// Copyright (c) 2011, the Dart project authors.  Please see the AUTHORS file
+// Copyright (c) 2013, 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.
 
@@ -418,6 +418,8 @@
 }
 
 void useHtmlEnhancedConfiguration([bool isLayoutTest = false]) {
-  if (config != null) return;
-  configure(new HtmlEnhancedConfiguration(isLayoutTest));
+  unittestConfiguration = isLayoutTest ? _singletonLayout : _singletonNotLayout;
 }
+
+final _singletonLayout = new HtmlEnhancedConfiguration(true);
+final _singletonNotLayout = new HtmlEnhancedConfiguration(false);
diff --git a/pkg/unittest/lib/html_individual_config.dart b/pkg/unittest/lib/html_individual_config.dart
index 2432a55..a031b78 100644
--- a/pkg/unittest/lib/html_individual_config.dart
+++ b/pkg/unittest/lib/html_individual_config.dart
@@ -1,4 +1,4 @@
-// Copyright (c) 2011, the Dart project authors.  Please see the AUTHORS file
+// Copyright (c) 2013, 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.
 
@@ -19,23 +19,24 @@
 import 'html_config.dart' as htmlconfig;
 
 class HtmlIndividualConfiguration extends htmlconfig.HtmlConfiguration {
-
-  String _noSuchTest = '';
-  HtmlIndividualConfiguration(isLayoutTest): super(isLayoutTest);
+  HtmlIndividualConfiguration(bool isLayoutTest): super(isLayoutTest);
 
   void onStart() {
     var search = window.location.search;
     if (search != '') {
-      try {
-        for (var parameter in search.substring(1).split('&')) {
-          if (parameter.startsWith('group=')) {
-            var testGroupName = parameter.split('=')[1];
-            unittest.filterTests('^$testGroupName${unittest.groupSep}');
-          }
+      var groups = search.substring(1).split('&')
+          .where((p) => p.startsWith('group='))
+          .toList();
+
+      if(!groups.isEmpty) {
+        if(groups.length > 1) {
+          throw 'More than one "group" parameter provided.';
         }
-      } catch (e) {
-        print('tried to match "$testGroupName"');
-        print('NO_SUCH_TEST');
+
+        var testGroupName = groups.single.split('=')[1];
+        var startsWith = "$testGroupName${unittest.groupSep}";
+        unittest.filterTests((unittest.TestCase tc) =>
+            tc.description.startsWith(startsWith));
       }
     }
     super.onStart();
@@ -43,6 +44,8 @@
 }
 
 void useHtmlIndividualConfiguration([bool isLayoutTest = false]) {
-  if (unittest.config != null) return;
-  unittest.configure(new HtmlIndividualConfiguration(isLayoutTest));
+  unittest.unittestConfiguration = isLayoutTest ? _singletonLayout : _singletonNotLayout;
 }
+
+final _singletonLayout = new HtmlIndividualConfiguration(true);
+final _singletonNotLayout = new HtmlIndividualConfiguration(false);
diff --git a/pkg/unittest/lib/html_layout_config.dart b/pkg/unittest/lib/html_layout_config.dart
deleted file mode 100644
index ddb0415..0000000
--- a/pkg/unittest/lib/html_layout_config.dart
+++ /dev/null
@@ -1,317 +0,0 @@
-// Copyright (c) 2013, 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 configuration for running layout tests with testrunner.
- * This configuration is similar to the interactive_html_config
- * as it runs each test in its own IFrame. However, where the former
- * recreated the IFrame for each test, here the IFrames are preserved.
- * Furthermore we post a message on completion.
- */
-library html_layout_config;
-
-import 'dart:async';
-import 'dart:html';
-import 'dart:math';
-import 'unittest.dart';
-
-/** The messages exchanged between parent and child. */
-// TODO(gram) At some point postMessage was supposed to support
-// sending arrays and maps. When it does we can get rid of the encoding/
-// decoding of messages as string.
-class _Message {
-  static final START = 'start';
-  static final LOG = 'log';
-  static final STACK = 'stack';
-  static final PASS = 'pass';
-  static final FAIL = 'fail';
-  static final ERROR = 'error';
-
-  String messageType;
-  int elapsed;
-  String body;
-
-  static String text(String messageType,
-                     [int elapsed = 0, String body = '']) =>
-      '$messageType $elapsed $body';
-
-  _Message(this.messageType, [this.elapsed = 0, this.body = '']);
-
-  _Message.fromString(String msg) {
-    // The format of a message is '<type> <elapsedTime> <body>'.
-    // If we don't get a type we default to a 'log' type.
-    var messageParser = new RegExp('\([a-z]*\) \([0-9]*\) \(.*\)');
-    Match match = messageParser.firstMatch(msg);
-    if (match == null) {
-      messageType = 'log';
-      elapsed = 0;
-      body = msg;
-    } else {
-      messageType = match.group(1);
-      elapsed = int.parse(match.group(2));
-      body = match.group(3);
-    }
-  }
-
-  String toString() => text(messageType, elapsed, body);
-}
-
-/**
- * The child configuration that is used to run individual tests in
- * an IFrame and post the results back to the parent. In principle
- * this can run more than one test in the IFrame but currently only
- * one is used.
- */
-class ChildHtmlConfiguration extends Configuration {
-  get name => 'ChildHtmlConfiguration';
-
-  StreamSubscription _errorSubscription;
-
-  /** The window to which results must be posted. */
-  Window parentWindow;
-
-  /** The time at which tests start. */
-  Map<int,DateTime> _testStarts;
-
-  ChildHtmlConfiguration() :
-      _testStarts = new Map<int,DateTime>();
-
-  /** Don't start running tests automatically. */
-  get autoStart => false;
-
-  void onInit() {
-    /**
-     *  The parent posts a 'start' message to kick things off,
-     *  which is handled by this handler. It saves the parent
-     *  window, gets the test ID from the query parameter in the
-     *  IFrame URL, sets that as a solo test and starts test execution.
-     */
-    window.onMessage.listen((MessageEvent e) {
-      var m = new _Message.fromString(e.data);
-      if (m.messageType == _Message.START) {
-        parentWindow = e.source;
-        String search = window.location.search;
-        int pos = search.indexOf('t=');
-        String ids = search.substring(pos+2);
-        int id = int.parse(ids);
-        setSoloTest(id);
-        runTests();
-      }
-    });
-  }
-
-  void onStart() {
-    _errorSubscription = window.onError.listen((e) {
-      handleExternalError(e, '(DOM callback has errors)');
-    });
-  }
-
-  /** Record the start time of the test. */
-  void onTestStart(TestCase testCase) {
-    super.onTestStart(testCase);
-    _testStarts[testCase.id]= new DateTime.now();
-  }
-
-  /**
-   * Tests can call [log] for diagnostic output. These log
-   * messages in turn get passed to this method, which adds
-   * a timestamp and posts them back to the parent window.
-   */
-  void logTestCaseMessage(TestCase testCase, String message) {
-    int elapsed;
-    if (testCase == null) {
-      elapsed = -1;
-    } else {
-      DateTime end = new DateTime.now();
-      elapsed = end.difference(_testStarts[testCase.id]).inMilliseconds;
-    }
-    parentWindow.postMessage(
-      _Message.text(_Message.LOG, elapsed, message).toString(), '*');
-  }
-
-  /**
-   * Get the elapsed time for the test, and post the test result
-   * back to the parent window. If the test failed due to an exception
-   * the stack is posted back too (before the test result).
-   */
-  void onTestResult(TestCase testCase) {
-    super.onTestResult(testCase);
-    DateTime end = new DateTime.now();
-    int elapsed = end.difference(_testStarts[testCase.id]).inMilliseconds;
-    if (testCase.stackTrace != null) {
-      parentWindow.postMessage(
-          _Message.text(_Message.STACK, elapsed, testCase.stackTrace), '*');
-    }
-    parentWindow.postMessage(
-        _Message.text(testCase.result, elapsed, testCase.message), '*');
-  }
-
-  void onSummary(int passed, int failed, int errors, List<TestCase> results,
-      String uncaughtError) {
-  }
-
-  void onDone(bool success) {
-    assert(_errorSubscription != null);
-    _errorSubscription.cancel();
-    _errorSubscription = null;
-  }
-}
-
-/**
- * The parent configuration runs in the top-level window; it wraps the tests
- * in new functions that create child IFrames and run the real tests.
- */
-class ParentHtmlConfiguration extends Configuration {
-  get autoStart => false;
-  get name => 'ParentHtmlConfiguration';
-  Map<int,DateTime> _testStarts;
-
-  /** The stack that was posted back from the child, if any. */
-  String _stack;
-
-  int _testTime;
-  /**
-   * Whether or not we have already wrapped the TestCase test functions
-   * in new closures that instead create an IFrame and get it to run the
-   * test.
-   */
-  bool _doneWrap = false;
-
-  StreamSubscription _messageSubscription, _errorSubscription;
-
-  ParentHtmlConfiguration() :
-      _testStarts = new Map<int,DateTime>();
-
-  // We need to block until the test is done, so we make a
-  // dummy async callback that we will use to flag completion.
-  Function completeTest = null;
-
-  wrapTest(TestCase testCase) {
-    String baseUrl = window.location.toString();
-    String url = '${baseUrl}?t=${testCase.id}';
-    return () {
-      // Add the child IFrame.
-      Element childDiv = document.query('#child');
-      var label = new Element.html(
-          "<pre id='result${testCase.id}'>${testCase.description}</pre>");
-      IFrameElement child = new Element.html("""
-          <iframe id='childFrame${testCase.id}' src='$url'>
-          </iframe>""");
-      childDiv.nodes.add(label);
-      childDiv.nodes.add(child);
-      completeTest = expectAsync0((){ });
-      // Kick off the test when the IFrame is loaded.
-      child.onLoad.listen((e) {
-        child.contentWindow.postMessage(_Message.text(_Message.START), '*');
-      });
-    };
-  }
-
-  void _handleMessage(MessageEvent e) {
-    // Get the result, do any logging, then do a pass/fail.
-    var msg = new _Message.fromString(e.data);
-    if (msg.messageType == _Message.LOG) {
-      logMessage(e.data);
-    } else if (msg.messageType == _Message.STACK) {
-      _stack = msg.body;
-    } else {
-      _testTime = msg.elapsed;
-      if (msg.messageType == _Message.PASS) {
-        currentTestCase.pass();
-      } else if (msg.messageType == _Message.FAIL) {
-        currentTestCase.fail(msg.body, _stack);
-      } else if (msg.messageType == _Message.ERROR) {
-        currentTestCase.error(msg.body, _stack);
-      }
-      completeTest();
-    }
-  }
-
-  void onInit() {
-  }
-
-  void onStart() {
-    // Listen for uncaught errors.
-    assert(_errorSubscription == null);
-    _errorSubscription = window.onError.listen((e) {
-      handleExternalError(e, '(DOM callback has errors)');
-    });
-
-    if (!_doneWrap) {
-      _doneWrap = true;
-      for (int i = 0; i < testCases.length; i++) {
-        testCases[i].testFunction = wrapTest(testCases[i]);
-        testCases[i].setUp = null;
-        testCases[i].tearDown = null;
-      }
-    }
-
-    _messageSubscription = window.onMessage.listen(_handleMessage);
-  }
-
-  void onTestStart(TestCase testCase) {
-    var id = testCase.id;
-    _testStarts[testCase.id]= new DateTime.now();
-    super.onTestStart(testCase);
-    _stack = null;
-  }
-
-  // Actually test logging is handled by the child, then posted
-  // back to the parent. So here we know that the [message] argument
-  // is in the format used by [_Message].
-  void logTestCaseMessage(TestCase testCase, String message) {
-    var msg = new _Message.fromString(message);
-    document.query('#otherlogs').nodes.add(
-          new Element.html('<p>${msg.body}</p>'));
-  }
-
-  void onTestResult(TestCase testCase) {
-    if (!testCase.enabled) return;
-    super.onTestResult(testCase);
-    document.query('#result${testCase.id}').text =
-        '${testCase.result}:${testCase.runningTime.inMilliseconds}:'
-        '${testCase.description}//${testCase.message}';
-  }
-
-  void onSummary(int passed, int failed, int errors, List<TestCase> results,
-      String uncaughtError) {
-  }
-  void onDone(bool success) {
-    _messageSubscription.cancel();
-    _messageSubscription = null;
-
-    _errorSubscription.cancel();
-    _errorSubscription = null;
-
-    window.postMessage('done', '*'); // Unblock DRT
-  }
-}
-
-/**
- * Add the divs to the DOM if they are not present.
- */
-void _prepareDom() {
-  if (document.query('#otherlogs') == null) {
-    document.body.nodes.add(new Element.html(
-        "<div id='otherlogs'></div>"));
-  }
-  if (document.query('#child') == null) {
-    document.body.nodes.add(new Element.html("<div id='child'></div>"));
-  }
-}
-
-/**
- * Allocate a Configuration. We allocate either a parent or
- * child, depending on whether the URL has a search part.
- */
-void useHtmlLayoutConfiguration() {
-  if (config != null) return;
-  if (window.location.search == '') { // This is the parent.
-    _prepareDom();
-    configure(new ParentHtmlConfiguration());
-  } else {
-    configure(new ChildHtmlConfiguration());
-  }
-}
-
diff --git a/pkg/unittest/lib/interactive_html_config.dart b/pkg/unittest/lib/interactive_html_config.dart
index 2475d53..a1d05c0 100644
--- a/pkg/unittest/lib/interactive_html_config.dart
+++ b/pkg/unittest/lib/interactive_html_config.dart
@@ -466,15 +466,17 @@
  * child, depending on whether the URL has a search part.
  */
 void useInteractiveHtmlConfiguration() {
-  if (config != null) return;
   if (window.location.search == '') { // This is the parent.
     _prepareDom();
-    configure(new ParentInteractiveHtmlConfiguration());
+    unittestConfiguration = _singletonParent;
   } else {
-    configure(new ChildInteractiveHtmlConfiguration());
+    unittestConfiguration = _singletonChild;
   }
 }
 
+final _singletonParent = new ParentInteractiveHtmlConfiguration();
+final _singletonChild = new ChildInteractiveHtmlConfiguration();
+
 String _CSS = """
 body {
 font-family: Arial, sans-serif;
diff --git a/pkg/unittest/lib/src/config.dart b/pkg/unittest/lib/src/config.dart
index 9b00394..b557783 100644
--- a/pkg/unittest/lib/src/config.dart
+++ b/pkg/unittest/lib/src/config.dart
@@ -49,7 +49,7 @@
    * a test suite.
    */
   void onTestStart(TestCase testCase) {
-    assert(testCase != null);	
+    assert(testCase != null);
   }
 
   /**
@@ -57,7 +57,7 @@
    * progress on a test suite.
    */
   void onTestResult(TestCase testCase) {
-    assert(testCase != null);	
+    assert(testCase != null);
   }
 
   /**
@@ -103,7 +103,7 @@
   void onSummary(int passed, int failed, int errors, List<TestCase> results,
       String uncaughtError) {
     // Print each test's result.
-    for (final t in _tests) {
+    for (final t in testCases) {
       var resultString = "${t.result}".toUpperCase();
       print('$resultString: ${t.description}');
 
diff --git a/pkg/unittest/lib/unittest.dart b/pkg/unittest/lib/unittest.dart
index 2132a3e..a0f5ffc 100644
--- a/pkg/unittest/lib/unittest.dart
+++ b/pkg/unittest/lib/unittest.dart
@@ -155,6 +155,7 @@
 
 import 'dart:async';
 import 'dart:isolate';
+import 'dart:collection';
 import 'matcher.dart';
 export 'matcher.dart';
 
@@ -165,20 +166,23 @@
 part 'src/config.dart';
 part 'src/test_case.dart';
 
-/** [Configuration] used by the unittest library. */
-Configuration _config = null;
+Configuration _config;
 
-Configuration get config => _config;
+/** [Configuration] used by the unittest library. */
+Configuration get unittestConfiguration => _config;
 
 /**
- * Set the [Configuration] used by the unittest library. Returns any
- * previous configuration.
- * TODO: consider deprecating in favor of a setter now we have a getter.
+ * Sets the [Configuration] used by the unittest library.
+ *
+ * Throws a [StateError] if there is an existing, incompatible value.
  */
-Configuration configure(Configuration config) {
-  Configuration _oldConfig = _config;
-  _config = config;
-  return _oldConfig;
+void set unittestConfiguration(Configuration value) {
+  if(!identical(_config, value)) {
+    if(_config != null) {
+      throw new StateError('unittestConfiguration has already been set');
+    }
+    _config = value;
+  }
 }
 
 void logMessage(String message) => _config.logMessage(message);
@@ -193,16 +197,10 @@
 String groupSep = ' ';
 
 /** Tests executed in this suite. */
-List<TestCase> _tests;
+final List<TestCase> _testCases = new List<TestCase>();
 
 /** Get the list of tests. */
-List<TestCase> get testCases => _tests;
-
-/**
- * Callback used to run tests. Entrypoints can replace this with their own
- * if they want.
- */
-Function _testRunner;
+final List<TestCase> testCases = new UnmodifiableListView(_testCases);
 
 /** Setup function called before each test in a group */
 Function _testSetup;
@@ -210,13 +208,12 @@
 /** Teardown function called after each test in a group */
 Function _testTeardown;
 
-/** Current test being executed. */
-int _currentTest = 0;
-TestCase _currentTestCase;
+int _currentTestCaseIndex = 0;
 
+/** [TestCase] currently being executed. */
 TestCase get currentTestCase =>
-    (_currentTest >= 0 && _currentTest < _tests.length)
-        ? _tests[_currentTest]
+    (_currentTestCaseIndex >= 0 && _currentTestCaseIndex < _testCases.length)
+        ? _testCases[_currentTestCaseIndex]
         : null;
 
 /** Whether the framework is in an initialized state. */
@@ -252,7 +249,8 @@
  */
 void test(String spec, TestFunction body) {
   ensureInitialized();
-  _tests.add(new TestCase._internal(_tests.length + 1, _fullSpec(spec), body));
+  _testCases.add(new TestCase._internal(_testCases.length + 1, _fullSpec(spec),
+                                        body));
 }
 
 /**
@@ -274,8 +272,8 @@
 
   ensureInitialized();
 
-  _soloTest = new TestCase._internal(_tests.length + 1, _fullSpec(spec), body);
-  _tests.add(_soloTest);
+  _soloTest = new TestCase._internal(_testCases.length + 1, _fullSpec(spec), body);
+  _testCases.add(_soloTest);
 }
 
 /** Sentinel value for [_SpreadArgsHelper]. */
@@ -306,19 +304,19 @@
             ? minExpected
             : maxExpected,
         this.isDone = isDone,
-        testNum = _currentTest,
+        testNum = _currentTestCaseIndex,
         this.id = _makeCallbackId(id, callback) {
     ensureInitialized();
-    if (!(_currentTest >= 0 &&
-           _currentTest < _tests.length &&
-           _tests[_currentTest] != null)) {
+    if (!(_currentTestCaseIndex >= 0 &&
+           _currentTestCaseIndex < _testCases.length &&
+           _testCases[_currentTestCaseIndex] != null)) {
       print("No valid test, did you forget to run your test inside a call "
           "to test()?");
     }
-    assert(_currentTest >= 0 &&
-           _currentTest < _tests.length &&
-           _tests[_currentTest] != null);
-    testCase = _tests[_currentTest];
+    assert(_currentTestCaseIndex >= 0 &&
+           _currentTestCaseIndex < _testCases.length &&
+           _testCases[_currentTestCaseIndex] != null);
+    testCase = _testCases[_currentTestCaseIndex];
     if (isDone != null || minExpected > 0) {
       testCase._callbackFunctionsOutstanding++;
       complete = false;
@@ -637,8 +635,8 @@
 /** Advance to the next test case. */
 void _nextTestCase() {
   _defer(() {
-    _currentTest++;
-    _testRunner();
+    _currentTestCaseIndex++;
+    _nextBatch();
   });
 }
 
@@ -647,8 +645,8 @@
  *  error was caught outside of this library.
  */
 void _reportTestError(String msg, String trace) {
- if (_currentTest < _tests.length) {
-    final testCase = _tests[_currentTest];
+ if (_currentTestCaseIndex < _testCases.length) {
+    final testCase = _testCases[_currentTestCaseIndex];
     testCase.error(msg, trace);
   } else {
     _uncaughtErrorMessage = "$msg: $trace";
@@ -689,12 +687,12 @@
   } else if (testFilter is Function) {
     filterFunction = testFilter;
   }
-  _tests.retainWhere(filterFunction);
+  _testCases.retainWhere(filterFunction);
 }
 
 /** Runs all queued tests, one at a time. */
 void runTests() {
-  _currentTest = 0;
+  _currentTestCaseIndex = 0;
   _currentGroup = '';
 
   // If we are soloing a test, remove all the others.
@@ -705,7 +703,7 @@
   _config.onStart();
 
   _defer(() {
-    _testRunner();
+    _nextBatch();
   });
 }
 
@@ -716,7 +714,7 @@
  * The value returned by [tryBody] (if any) is returned by [guardAsync].
  */
 guardAsync(Function tryBody) {
-  return _guardAsync(tryBody, null, _currentTest);
+  return _guardAsync(tryBody, null, _currentTestCaseIndex);
 }
 
 _guardAsync(Function tryBody, Function finallyBody, int testNum) {
@@ -734,19 +732,19 @@
  * Registers that an exception was caught for the current test.
  */
 void registerException(e, [trace]) {
-  _registerException(_currentTest, e, trace);
+  _registerException(_currentTestCaseIndex, e, trace);
 }
 
 /**
  * Registers that an exception was caught for the current test.
  */
-_registerException(testNum, e, [trace]) {
+void _registerException(testNum, e, [trace]) {
   trace = trace == null ? '' : trace.toString();
   String message = (e is TestFailure) ? e.message : 'Caught $e';
-  if (_tests[testNum].result == null) {
-    _tests[testNum].fail(message, trace);
+  if (_testCases[testNum].result == null) {
+    _testCases[testNum].fail(message, trace);
   } else {
-    _tests[testNum].error(message, trace);
+    _testCases[testNum].error(message, trace);
   }
 }
 
@@ -755,39 +753,39 @@
  * running. Tests will resume executing when such asynchronous test calls
  * [done] or if it fails with an exception.
  */
-_nextBatch() {
+void _nextBatch() {
   while (true) {
-    if (_currentTest >= _tests.length) {
+    if (_currentTestCaseIndex >= _testCases.length) {
       _completeTests();
       break;
     }
-    final testCase = _tests[_currentTest];
-    var f = _guardAsync(testCase._run, null, _currentTest);
+    final testCase = _testCases[_currentTestCaseIndex];
+    var f = _guardAsync(testCase._run, null, _currentTestCaseIndex);
     if (f != null) {
       f.whenComplete(() {
         _nextTestCase(); // Schedule the next test.
       });
       break;
     }
-    _currentTest++;
+    _currentTestCaseIndex++;
   }
 }
 
 /** Publish results on the page and notify controller. */
-_completeTests() {
+void _completeTests() {
   if (!_initialized) return;
   int passed = 0;
   int failed = 0;
   int errors = 0;
 
-  for (TestCase t in _tests) {
+  for (TestCase t in _testCases) {
     switch (t.result) {
       case PASS:  passed++; break;
       case FAIL:  failed++; break;
       case ERROR: errors++; break;
     }
   }
-  _config.onSummary(passed, failed, errors, _tests, _uncaughtErrorMessage);
+  _config.onSummary(passed, failed, errors, _testCases, _uncaughtErrorMessage);
   _config.onDone(passed > 0 && failed == 0 && errors == 0 &&
       _uncaughtErrorMessage == null);
   _initialized = false;
@@ -809,12 +807,10 @@
   // Hook our async guard into the matcher library.
   wrapAsync = (f, [id]) => expectAsync1(f, id: id);
 
-  _tests = <TestCase>[];
-  _testRunner = _nextBatch;
   _uncaughtErrorMessage = null;
 
   if (_config == null) {
-    _config = new Configuration();
+    unittestConfiguration = new Configuration();
   }
   _config.onInit();
 
@@ -827,9 +823,9 @@
 
 /** Select a solo test by ID. */
 void setSoloTest(int id) {
-  for (var i = 0; i < _tests.length; i++) {
-    if (_tests[i].id == id) {
-      _soloTest = _tests[i];
+  for (var i = 0; i < _testCases.length; i++) {
+    if (_testCases[i].id == id) {
+      _soloTest = _testCases[i];
       break;
     }
   }
@@ -838,12 +834,12 @@
 /** Enable/disable a test by ID. */
 void _setTestEnabledState(int testId, bool state) {
   // Try fast path first.
-  if (_tests.length > testId && _tests[testId].id == testId) {
-    _tests[testId].enabled = state;
+  if (_testCases.length > testId && _testCases[testId].id == testId) {
+    _testCases[testId].enabled = state;
   } else {
-    for (var i = 0; i < _tests.length; i++) {
-      if (_tests[i].id == testId) {
-        _tests[i].enabled = state;
+    for (var i = 0; i < _testCases.length; i++) {
+      if (_testCases[i].id == testId) {
+        _testCases[i].enabled = state;
         break;
       }
     }
diff --git a/pkg/unittest/lib/vm_config.dart b/pkg/unittest/lib/vm_config.dart
index 1f4ce0d..9d2e6ea 100644
--- a/pkg/unittest/lib/vm_config.dart
+++ b/pkg/unittest/lib/vm_config.dart
@@ -1,4 +1,4 @@
-// Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file
+// Copyright (c) 2013, 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.
 
@@ -9,7 +9,6 @@
 
 import 'dart:io';
 import 'unittest.dart';
-import 'package:meta/meta.dart';
 
 class VMConfiguration extends Configuration {
   void onDone(bool success) {
@@ -25,9 +24,7 @@
 }
 
 void useVMConfiguration() {
-  if (config != null) return;
-  configure(new VMConfiguration());
+  unittestConfiguration = _singleton;
 }
 
-@deprecated
-void useVmConfiguration() => useVMConfiguration();
+final _singleton = new VMConfiguration();
diff --git a/pkg/unittest/test/unittest_test.dart b/pkg/unittest/test/unittest_test.dart
index e0127bd..7f62c50 100644
--- a/pkg/unittest/test/unittest_test.dart
+++ b/pkg/unittest/test/unittest_test.dart
@@ -17,7 +17,6 @@
 var tests; // array of test names
 var expected; // array of test expected results (from buildStatusString)
 var actual; // actual test results (from buildStatusString in config.onDone)
-var _testconfig; // test configuration to capture onDone
 
 Future _defer(void fn()) {
   return new Future.of(fn);
@@ -54,7 +53,7 @@
   String teardown = ''; // the name of the test group teardown function, if any
 
   // The port to communicate with the parent isolate
-  SendPort _port;
+  final SendPort _port;
   String _result;
 
   TestConfiguration(this._port);
@@ -73,7 +72,9 @@
 
 runTest() {
   port.receive((testName, sendport) {
-    configure(_testconfig = new TestConfiguration(sendport));
+    var _testconfig= new TestConfiguration(sendport);
+    unittestConfiguration = _testconfig;
+
     if (testName == 'single correct test') {
       test(testName, () => expect(2 + 3, equals(5)));
     } else if (testName == 'single failing test') {
@@ -293,6 +294,11 @@
       });
       test('foo6', () {
       });
+    } else if (testName == 'testCases immutable') {
+      test(testName, () {
+        expect(() => testCases.clear(), throwsUnsupportedError);
+        expect(() => testCases.removeLast(), throwsUnsupportedError);
+      });
     }
   });
 }
@@ -328,7 +334,8 @@
     'middle exception test',
     'async setup/teardown test',
     'test returning future',
-    'test returning future using Timer'
+    'test returning future using Timer',
+    'testCases immutable'
   ];
 
   expected = [
@@ -375,6 +382,7 @@
         'fail2:failure:'
         'error2:Callback called more times than expected (1).:'
         'foo6'),
+    buildStatusString(1, 0, 0, 'testCases immutable'),
   ];
 
   actual = [];
diff --git a/runtime/bin/io.dart b/runtime/bin/io.dart
index 5e47d9f..92ca329 100644
--- a/runtime/bin/io.dart
+++ b/runtime/bin/io.dart
@@ -6,13 +6,13 @@
 // the dart:io library for the VM because it cannot use the actual library
 // file which is in lib/io/io.dart.
 
-#library("dart:io");
-#import("dart:async");
-#import("dart:collection");
-#import("dart:crypto");
-#import("dart:isolate");
-#import("dart:math");
-#import("dart:nativewrappers");
-#import("dart:typeddata");
-#import("dart:uri");
-#import("dart:utf");
+library dart.io;
+import "dart:async";
+import "dart:collection";
+import "dart:crypto";
+import "dart:isolate";
+import "dart:math";
+import "dart:nativewrappers";
+import "dart:typeddata";
+import "dart:uri";
+import "dart:utf";
diff --git a/runtime/bin/vmstats_impl.cc b/runtime/bin/vmstats_impl.cc
index 90e3d53..b05614e 100644
--- a/runtime/bin/vmstats_impl.cc
+++ b/runtime/bin/vmstats_impl.cc
@@ -4,8 +4,6 @@
 
 #include "bin/vmstats_impl.h"
 
-#include <sstream>
-
 #include "bin/file.h"
 #include "bin/log.h"
 #include "bin/platform.h"
@@ -252,21 +250,22 @@
       free(content);
     } else {
       // No status content with this URL, return file or resource content.
-      std::string path(instance_->root_directory_);
-      path.append(url);
+      dart::TextBuffer path(strlen(instance_->root_directory_) + strlen(url));
+      path.AddString(instance_->root_directory_);
+      path.AddString(url);
 
       // Expand directory URLs.
       if (strcmp(url, "/") == 0) {
-        path.append(VMSTATS_HTML);
+        path.AddString(VMSTATS_HTML);
       } else if (url[strlen(url) - 1] == '/') {
-        path.append(INDEX_HTML);
+        path.AddString(INDEX_HTML);
       }
 
       bool success = false;
       char* text_buffer = NULL;
-      const char* content_type = ContentType(path.c_str());
-      if (File::Exists(path.c_str())) {
-        File* f = File::Open(path.c_str(), File::kRead);
+      const char* content_type = ContentType(path.buf());
+      if (File::Exists(path.buf())) {
+        File* f = File::Open(path.buf(), File::kRead);
         if (f != NULL) {
           intptr_t len = f->Length();
           text_buffer = reinterpret_cast<char*>(malloc(len));
@@ -279,7 +278,7 @@
         }
       } else {
         const char* resource;
-        intptr_t len = Resources::ResourceLookup(path.c_str(), &resource);
+        intptr_t len = Resources::ResourceLookup(path.buf(), &resource);
         if (len != Resources::kNoSuchInstance) {
           ASSERT(len >= 0);
           writeResponse(socket, content_type, resource, len);
@@ -303,9 +302,8 @@
 
 
 char* VmStats::IsolatesStatus() {
-  std::ostringstream stream;
-  stream << '{' << std::endl;
-  stream << "\"isolates\": [" << std::endl;
+  dart::TextBuffer text(64);
+  text.Printf("{\n\"isolates\": [\n");
   IsolateTable::iterator itr;
   bool first = true;
   for (itr = isolate_table_.begin(); itr != isolate_table_.end(); ++itr) {
@@ -316,17 +314,16 @@
              reinterpret_cast<intptr_t>(isolate));
     char* status = VmStatusService::GetVmStatus(request);
     if (status != NULL) {
-      stream << status;
+      text.AddString(status);
       if (!first) {
-        stream << "," << std::endl;
+        text.AddString(",\n");
       }
       first = false;
+      free(status);
     }
-    free(status);
   }
-  stream << std::endl << "]";
-  stream << std::endl << '}' << std::endl;
-  return strdup(stream.str().c_str());
+  text.AddString("\n]\n}\n");
+  return strdup(text.buf());
 }
 
 
diff --git a/runtime/bin/vmstats_impl.h b/runtime/bin/vmstats_impl.h
index 63749b3..b39f2ce 100644
--- a/runtime/bin/vmstats_impl.h
+++ b/runtime/bin/vmstats_impl.h
@@ -8,8 +8,6 @@
 #include "bin/vmstats.h"
 
 #include <map>
-#include <sstream>
-#include <string>
 
 #include "bin/isolate_data.h"
 #include "platform/thread.h"
@@ -27,7 +25,7 @@
   static void RemoveIsolate(IsolateData* isolate_data);
 
  private:
-  VmStats() : running_(false), bind_address_(0) {}
+  VmStats() : root_directory_(NULL), running_(false), bind_address_(0) {}
 
   static void WebServer(uword bind_address);
   static void Shutdown();
@@ -37,7 +35,7 @@
 
   typedef std::map<IsolateData*, Dart_Isolate> IsolateTable;
 
-  std::string root_directory_;
+  const char* root_directory_;
   IsolateTable isolate_table_;
   bool running_;
   int64_t bind_address_;
diff --git a/runtime/embedders/openglui/android/android_input_handler.h b/runtime/embedders/openglui/android/android_input_handler.h
index b39510a..d1e8d2a 100644
--- a/runtime/embedders/openglui/android/android_input_handler.h
+++ b/runtime/embedders/openglui/android/android_input_handler.h
@@ -5,6 +5,7 @@
 #ifndef EMBEDDERS_OPENGLUI_ANDROID_ANDROID_INPUT_HANDLER_H_
 #define EMBEDDERS_OPENGLUI_ANDROID_ANDROID_INPUT_HANDLER_H_
 
+#include "embedders/openglui/android/android_sensor.h"
 #include "embedders/openglui/common/graphics_handler.h"
 #include "embedders/openglui/common/input_handler.h"
 
@@ -25,6 +26,9 @@
       return 0;
     }
 
+    void Stop() {
+    }
+
   private:
     GraphicsHandler* graphics_handler_;
 };
diff --git a/runtime/embedders/openglui/android/android_sound_handler.cc b/runtime/embedders/openglui/android/android_sound_handler.cc
index 8d0b2b7..a40c1ba 100644
--- a/runtime/embedders/openglui/android/android_sound_handler.cc
+++ b/runtime/embedders/openglui/android/android_sound_handler.cc
@@ -264,6 +264,8 @@
         res = (*sample_player_queue_)->Enqueue(sample_player_queue_,
                                                buffer, len);
         if (res == SL_RESULT_SUCCESS) {
+          LOGE("Enqueued sample %s of length %d", path,
+            static_cast<int>(len));
           return 0;
         }
         LOGE("Enqueueing sample failed");
diff --git a/runtime/embedders/openglui/android/eventloop.cc b/runtime/embedders/openglui/android/eventloop.cc
index b247008..ed1645e 100644
--- a/runtime/embedders/openglui/android/eventloop.cc
+++ b/runtime/embedders/openglui/android/eventloop.cc
@@ -4,6 +4,7 @@
 
 #include "embedders/openglui/android/eventloop.h"
 
+#include <time.h>
 #include "embedders/openglui/common/log.h"
 
 /*
@@ -154,12 +155,21 @@
       hasFocus_(false),
       application_(application),
       lifecycle_handler_(NULL),
-      input_handler_(NULL) {
+      input_handler_(NULL),
+      sensor_manager_(NULL),
+      sensor_event_queue_(NULL),
+      sensor_poll_source_() {
   application_->onAppCmd = ActivityCallback;
   application_->onInputEvent = InputCallback;
   application_->userData = this;
 }
 
+static int64_t getTimeInMillis() {
+  struct timespec res;
+  clock_gettime(CLOCK_REALTIME, &res);
+  return 1000 * res.tv_sec + res.tv_nsec / 1000000;
+}
+
 void EventLoop::Run(LifeCycleHandler* lifecycle_handler,
                     InputHandler* input_handler) {
   int32_t result;
@@ -168,14 +178,17 @@
 
   lifecycle_handler_ = lifecycle_handler;
   input_handler_ = input_handler;
+  int64_t last_frame_time = getTimeInMillis();
   if (lifecycle_handler_->OnStart() == 0) {
     LOGI("Starting event loop");
     while (!quit_) {
       // If not enabled, block indefinitely on events. If enabled, block
-      // briefly so we can do useful work in onStep. Ultimately this is
-      // where we would want to look at elapsed time since the last call
-      // to onStep completed and use a delay that gives us ~60fps.
-      while ((result = ALooper_pollAll(enabled_ ? (1000/60) : -1, NULL,
+      // briefly so we can do useful work in onStep, but only long
+      // enough that we can still do work at 60fps if possible.
+      int64_t next_frame_time = last_frame_time + (1000/60);
+      int64_t next_frame_delay = next_frame_time - getTimeInMillis();
+      if (next_frame_delay < 0) next_frame_delay = 0;
+      while ((result = ALooper_pollAll(enabled_ ? next_frame_delay : -1, NULL,
           &events, reinterpret_cast<void**>(&source))) >= 0) {
         if (source != NULL) {
           source->process(application_, source);
@@ -185,9 +198,13 @@
         }
       }
       if (enabled_ && !quit_) {
-        LOGI("step");
-        if (lifecycle_handler_->OnStep() != 0) {
-          quit_ = true;
+        int64_t now = getTimeInMillis();
+        if (now >= next_frame_time) {
+          LOGI("step");
+          last_frame_time = now;
+          if (lifecycle_handler_->OnStep() != 0) {
+            quit_ = true;
+          }
         }
       }
     }
@@ -195,6 +212,53 @@
   ANativeActivity_finish(application_->activity);
 }
 
+void EventLoop::EnableSensorEvents() {
+  sensor_poll_source_.id = LOOPER_ID_USER;
+  sensor_poll_source_.app = application_;
+  sensor_poll_source_.process = SensorCallback;
+  sensor_manager_ = ASensorManager_getInstance();
+  if (sensor_manager_ != NULL) {
+    sensor_event_queue_ = ASensorManager_createEventQueue(
+        sensor_manager_, application_->looper,
+        LOOPER_ID_USER, NULL, &sensor_poll_source_);
+
+    sensor_ = ASensorManager_getDefaultSensor(sensor_manager_,
+        ASENSOR_TYPE_ACCELEROMETER);
+    if (sensor_ != NULL) {
+      int32_t min_delay = ASensor_getMinDelay(sensor_);
+      if (ASensorEventQueue_enableSensor(sensor_event_queue_, sensor_) < 0 ||
+          ASensorEventQueue_setEventRate(sensor_event_queue_, sensor_,
+              min_delay) < 0) {
+        LOGE("Error while activating sensor.");
+        DisableSensorEvents();
+        return;
+      }
+      LOGI("Activating sensor:");
+      LOGI("Name       : %s", ASensor_getName(sensor_));
+      LOGI("Vendor     : %s", ASensor_getVendor(sensor_));
+      LOGI("Resolution : %f", ASensor_getResolution(sensor_));
+      LOGI("Min Delay  : %d", min_delay);
+    } else {
+      LOGI("No sensor");
+    }
+  }
+}
+
+void EventLoop::DisableSensorEvents() {
+  if (sensor_ != NULL) {
+    if (ASensorEventQueue_disableSensor(sensor_event_queue_, sensor_) < 0) {
+      LOGE("Error while deactivating sensor.");
+    }
+    sensor_ = NULL;
+  }
+  if (sensor_event_queue_ != NULL) {
+    ASensorManager_destroyEventQueue(sensor_manager_,
+                    sensor_event_queue_);
+    sensor_event_queue_ = NULL;
+  }
+  sensor_manager_ = NULL;
+}
+
 void EventLoop::ProcessActivityEvent(int32_t command) {
   switch (command) {
     case APP_CMD_INIT_WINDOW:
@@ -215,11 +279,15 @@
       hasFocus_ = true;
       if (hasSurface_ && isResumed_ && hasFocus_) {
         enabled_ = (lifecycle_handler_->Resume() == 0);
+        if (enabled_) {
+          EnableSensorEvents();
+        }
       }
       break;
     case APP_CMD_LOST_FOCUS:
       hasFocus_ = false;
       enabled_ = false;
+      DisableSensorEvents();
       lifecycle_handler_->Pause();
       break;
     case APP_CMD_LOW_MEMORY:
@@ -228,6 +296,7 @@
     case APP_CMD_PAUSE:
       isResumed_ = false;
       enabled_ = false;
+      DisableSensorEvents();
       lifecycle_handler_->Pause();
       break;
     case APP_CMD_RESUME:
@@ -247,6 +316,7 @@
       hasFocus_ = false;
       hasSurface_ = false;
       enabled_ = false;
+      DisableSensorEvents();
       lifecycle_handler_->Pause();
       break;
     default:
@@ -254,6 +324,18 @@
   }
 }
 
+void EventLoop::ProcessSensorEvent() {
+  ASensorEvent event;
+  while (ASensorEventQueue_getEvents(sensor_event_queue_, &event, 1) > 0) {
+    switch (event.type) {
+      case ASENSOR_TYPE_ACCELEROMETER:
+        input_handler_->OnAccelerometerEvent(event.vector.x,
+            event.vector.y, event.vector.z);
+        break;
+    }
+  }
+}
+
 bool EventLoop::OnTouchEvent(AInputEvent* event) {
   int32_t type = AMotionEvent_getAction(event);
   MotionEvent motion_event;
@@ -310,7 +392,6 @@
     default:
       return false;
   }
-  int32_t flags = AKeyEvent_getFlags(event);
   /* Get the key code of the key event.
    * This is the physical key that was pressed, not the Unicode character. */
   int32_t key_code = AKeyEvent_getKeyCode(event);
@@ -375,3 +456,9 @@
   return event_loop->ProcessInputEvent(event);
 }
 
+void EventLoop::SensorCallback(android_app* application,
+    android_poll_source* source) {
+  EventLoop* event_loop = reinterpret_cast<EventLoop*>(application->userData);
+  event_loop->ProcessSensorEvent();
+}
+
diff --git a/runtime/embedders/openglui/android/eventloop.h b/runtime/embedders/openglui/android/eventloop.h
index 2c548c8..031bf69 100644
--- a/runtime/embedders/openglui/android/eventloop.h
+++ b/runtime/embedders/openglui/android/eventloop.h
@@ -6,6 +6,7 @@
 #define EMBEDDERS_OPENGLUI_ANDROID_EVENTLOOP_H_
 
 #include <android_native_app_glue.h>
+#include <android/sensor.h>
 #include "embedders/openglui/common/events.h"
 #include "embedders/openglui/common/input_handler.h"
 #include "embedders/openglui/common/lifecycle_handler.h"
@@ -17,20 +18,33 @@
              InputHandler* input_handler);
 
   protected:
+    void EnableSensorEvents();
+    void DisableSensorEvents();
+
     void ProcessActivityEvent(int32_t command);
     int32_t ProcessInputEvent(AInputEvent* event);
+    void ProcessSensorEvent();
+
     bool OnTouchEvent(AInputEvent* event);
     bool OnKeyEvent(AInputEvent* event);
 
     static void ActivityCallback(android_app* application, int32_t command);
     static int32_t InputCallback(android_app* application, AInputEvent* event);
+    static void SensorCallback(android_app* application,
+        android_poll_source* source);
 
   private:
+    friend class Sensor;
+
     bool enabled_, quit_;
     bool isResumed_, hasSurface_, hasFocus_;
     android_app* application_;
     LifeCycleHandler* lifecycle_handler_;
     InputHandler* input_handler_;
+    const ASensor* sensor_;
+    ASensorManager* sensor_manager_;
+    ASensorEventQueue* sensor_event_queue_;
+    android_poll_source sensor_poll_source_;
 };
 
 #endif  // EMBEDDERS_OPENGLUI_ANDROID_EVENTLOOP_H_
diff --git a/runtime/embedders/openglui/android/main.cc b/runtime/embedders/openglui/android/main.cc
index 5569627..4844a3d 100644
--- a/runtime/embedders/openglui/android/main.cc
+++ b/runtime/embedders/openglui/android/main.cc
@@ -4,15 +4,25 @@
 
 #include "embedders/openglui/android/android_graphics_handler.h"
 #include "embedders/openglui/android/android_input_handler.h"
+#include "embedders/openglui/android/android_resource.h"
+#include "embedders/openglui/android/android_sensor.h"
 #include "embedders/openglui/android/android_sound_handler.h"
 #include "embedders/openglui/android/eventloop.h"
 #include "embedders/openglui/common/context.h"
 #include "embedders/openglui/common/dart_host.h"
 #include "embedders/openglui/common/vm_glue.h"
 
+android_app* application_ = NULL;
+
+Resource* MakePlatformResource(const char *path) {
+  return new AndroidResource(application_, path);
+}
+
 void android_main(android_app* application) {
+  application_ = application;
   app_dummy();  // Link in native_app_glue.
   const char* resource_path = "/data/data/com.google.dartndk/app_dart";
+  EventLoop eventLoop(application);
   AndroidGraphicsHandler graphics_handler(application, resource_path);
   VMGlue vm_glue(&graphics_handler, resource_path);
   AndroidInputHandler input_handler(&vm_glue, &graphics_handler);
@@ -24,7 +34,6 @@
   app_context.sound_handler = &sound_handler;
   app_context.timer = &timer;
   app_context.vm_glue = &vm_glue;
-  EventLoop eventLoop(application);
   DartHost host(&app_context);
   eventLoop.Run(&host, &input_handler);
 }
diff --git a/runtime/embedders/openglui/build_skia.sh b/runtime/embedders/openglui/build_skia.sh
index 92b30ea..9eca1dc 100755
--- a/runtime/embedders/openglui/build_skia.sh
+++ b/runtime/embedders/openglui/build_skia.sh
@@ -1,19 +1,21 @@
 #!/bin/bash
 
 function usage {
-  echo "usage: $0 [ --help ] [ --android ] [ --arm | --x86] [--clean] [<Dart directory>]"
+  echo "usage: $0 [ --help ] [ --android ] [ --arm | --x86] [ --debug ] [--clean] [<Dart directory>]"
   echo
   echo "Sync up Skia and build"
   echo
   echo " --android: Build for Android"
   echo " --x86 : Build for Intel"
   echo " --arm : Cross-compile for ARM (implies --android)"
+  echo " --debug : Build a debug version"
   echo
 }
 
 DO_ANDROID=0
 TARGET_ARCH=x86
 CLEAN=0
+BUILD=Release
 DART_DIR=../../..
 
 while [ ! -z "$1" ] ; do
@@ -35,6 +37,12 @@
     "--clean")
       CLEAN=1
     ;;
+    "--debug")
+      BUILD=Debug
+    ;;
+    "--release")
+      BUILD=Release
+    ;;
     *)
       if [ ! -d "$1" ]
       then
@@ -64,10 +72,7 @@
   if [ ${CLEAN} != 0 ] ; then
     ../android/bin/android_make -d $TARGET_ARCH -j clean
   else
-    env -i BUILDTYPE=Debug ANDROID_SDK_ROOT="${ANDROID_SDK_ROOT}" ../android/bin/android_make BUILDTYPE=Debug -d $TARGET_ARCH -j --debug=j
-    #../android/bin/android_make ANDROID_NDK= BUILDTYPE=Debug ANDROID_SDK_ROOT= -d $TARGET_ARCH -j
-    #../android/bin/android_make ANDROID_NDK= BUILDTYPE=Debug ANDROID_SDK_ROOT="${ANDROID_SDK_ROOT}" -d $TARGET_ARCH -j
-    #../android/bin/android_make BUILDTYPE=Debug ANDROID_SDK_ROOT="${ANDROID_SDK_ROOT}" -d $TARGET_ARCH -j png
+    env -i BUILDTYPE=$BUILD ANDROID_SDK_ROOT="${ANDROID_SDK_ROOT}" ../android/bin/android_make BUILDTYPE=$BUILD -d $TARGET_ARCH -j --debug=j
   fi
 
 else
@@ -92,7 +97,7 @@
     make clean
   else
     # Dart sets BUILDTYPE to DebugX64 which breaks Skia build.
-    make BUILDTYPE=Debug
+    make BUILDTYPE=$BUILD
   fi
   cd ..
 
diff --git a/runtime/embedders/openglui/common/canvas_context.cc b/runtime/embedders/openglui/common/canvas_context.cc
index 851a30d..24c0f7d 100644
--- a/runtime/embedders/openglui/common/canvas_context.cc
+++ b/runtime/embedders/openglui/common/canvas_context.cc
@@ -7,10 +7,11 @@
 #include <ctype.h>
 #include <string.h>
 #include "core/SkStream.h"
+#include "embedders/openglui/common/image_cache.h"
 #include "embedders/openglui/common/support.h"
 
 // TODO(gram): this should be dynamic.
-#define MAX_CONTEXTS 16
+#define MAX_CONTEXTS 256
 CanvasContext* contexts[MAX_CONTEXTS] = { 0 };
 
 CanvasContext* Context2D(int handle) {
@@ -40,6 +41,10 @@
     height_(heightp),
     imageSmoothingEnabled_(true),
     state_(NULL) {
+  if (handle >= MAX_CONTEXTS) {
+    LOGE("Max contexts exceeded");
+    exit(-1);
+  }
   if (handle == 0) {
     canvas_ = graphics->CreateDisplayCanvas();
   } else {
@@ -55,68 +60,39 @@
   delete canvas_;
 }
 
+void CanvasContext::Save() {
+  state_ = state_->Save();
+}
+
+void CanvasContext::Restore() {
+  CanvasState* popped_state = state_;
+  state_ = state_->Restore();
+  if (state_ == NULL) {
+    LOGE("Popping last state!");
+    state_ = popped_state;
+  }
+  if (state_ != popped_state) {
+    // Only delete if the pop was successful.
+    delete popped_state;
+  }
+}
+
 void CanvasContext::DrawImage(const char* src_url,
                               int sx, int sy,
                               bool has_src_dimensions, int sw, int sh,
                               int dx, int dy,
                               bool has_dst_dimensions, int dw, int dh) {
-  SkBitmap bm;
-  if (strncmp(src_url, "context2d://", 12) == 0) {
-    int handle = atoi(src_url + 12);
-    CanvasContext* otherContext = Context2D(handle);
-    SkDevice* device = otherContext->canvas_->getDevice();
-    bm = device->accessBitmap(false);
-  } else {
-    const char* filepath;
-    if (strncmp(src_url, "file://", 7) == 0) {
-      filepath = src_url + 7;
-    } else {
-      // TODO(gram): We need a way to remap URLs to local file names.
-      // For now I am just using the characters after the last '/'.
-      // Note also that if we want to support URLs and network fetches,
-      // then we introduce more complexity; this can't just be an URL.
-      int pos = strlen(src_url);
-      while (--pos >= 0 && src_url[pos] != '/');
-      filepath = src_url + pos + 1;
-    }
-    char* path;
-    if (filepath[0] == '/') {
-      path = const_cast<char*>(filepath);
-    } else {
-      size_t len1 = strlen(graphics->resource_path());
-      size_t len2 = strlen(filepath);
-      path = new char[len1 + 1 + len2 + 1];
-      strncpy(path, graphics->resource_path(), len1+1);
-      strncat(path, "/", 1);
-      strncat(path, filepath, len2);
-    }
-    SkFILEStream stream(path);
-    if (stream.isValid()) {
-      // We could use DecodeFile and pass the path, but by creating the
-      // SkStream here we can produce better error log messages.
-      if (!SkImageDecoder::DecodeStream(&stream, &bm)) {
-        LOGI("Image decode of %s failed", path);
-        return;
-      } else {
-        LOGI("Decode image %s: width=%d,height=%d",
-            path, bm.width(), bm.height());
-      }
-    } else {
-      LOGI("Path %s is invalid", path);
-    }
-    if (path != filepath) {
-      delete[] path;
-    }
-  }
+  const SkBitmap* bm = ImageCache::GetImage(src_url);
+  if (bm == NULL) return;
   if (!has_src_dimensions) {
-    sw = bm.width();
-    sh = bm.height();
+    sw = bm->width();
+    sh = bm->height();
   }
   if (!has_dst_dimensions) {
-    dw = bm.width();
-    dh = bm.height();
+    dw = bm->width();
+    dh = bm->height();
   }
-  state_->DrawImage(bm, sx, sy, sw, sh, dx, dy, dw, dh);
+  state_->DrawImage(*bm, sx, sy, sw, sh, dx, dy, dw, dh);
   isDirty_ = true;
 }
 
diff --git a/runtime/embedders/openglui/common/canvas_context.h b/runtime/embedders/openglui/common/canvas_context.h
index 3fc44ef..a45b574 100644
--- a/runtime/embedders/openglui/common/canvas_context.h
+++ b/runtime/embedders/openglui/common/canvas_context.h
@@ -103,18 +103,8 @@
     state_->setGlobalCompositeOperation(op);
   }
 
-  inline void Save() {
-    state_ = state_->Save();
-  }
-
-  inline void Restore() {
-    CanvasState* popped_state = state_;
-    state_ = state_->Restore();
-    if (state_ != popped_state) {
-      // Only delete if the pop was successful.
-      delete popped_state;
-    }
-  }
+  void Save();
+  void Restore();
 
   inline void Rotate(float angle) {
     canvas_->rotate(Radians2Degrees(angle));
@@ -306,6 +296,25 @@
   virtual void Flush() {
     canvas_->flush();
   }
+
+  inline void SetFillGradient(bool is_radial, double x0, double y0, double r0,
+      double x1, double y1, double r1,
+      int stops, float* positions, char** colors) {
+    state_->SetFillGradient(is_radial, x0, y0, r0, x1, y1, r1,
+        stops, positions, colors);
+  }
+
+  inline void SetStrokeGradient(bool is_radial, double x0, double y0, double r0,
+      double x1, double y1, double r1,
+      int stops, float* positions, char** colors) {
+    state_->SetStrokeGradient(is_radial, x0, y0, r0, x1, y1, r1,
+        stops, positions, colors);
+  }
+
+  inline const SkBitmap* GetBitmap() {
+    SkDevice* device = canvas_->getDevice();
+    return &device->accessBitmap(false);
+  }
 };
 
 CanvasContext* Context2D(int handle);
diff --git a/runtime/embedders/openglui/common/canvas_state.cc b/runtime/embedders/openglui/common/canvas_state.cc
index 16232b9..8d927c8 100644
--- a/runtime/embedders/openglui/common/canvas_state.cc
+++ b/runtime/embedders/openglui/common/canvas_state.cc
@@ -47,6 +47,22 @@
   return rtn;
 }
 
+CanvasState* CanvasState::Restore() {
+  if (next_ != NULL) {
+    // If the state we are popping has a non-empty path,
+    // apply the state's transform to the path, then
+    // add the path to the previous state's path.
+    if (path_->countPoints() > 0) {
+      path_->transform(canvas_->getTotalMatrix());
+      next_->path_->addPath(*path_);
+    }
+    canvas_->restore();
+    return next_;
+  }
+  canvas_->restore();
+  return next_;  // TODO(gram): Should we assert/throw?
+}
+
 void CanvasState::setLineCap(const char* lc) {
   if (strcmp(lc, "round") == 0) {
     paint_.setStrokeCap(SkPaint::kRound_Cap);
@@ -137,6 +153,29 @@
   return direction;
 }
 
+void CanvasState::setMode(SkPaint::Style style, ColorRGBA color,
+    SkShader* shader) {
+  paint_.setStyle(style);
+  paint_.setColor(color.v);
+  paint_.setShader(shader);
+  uint8_t alpha = static_cast<uint8_t>(
+      globalAlpha_ * static_cast<float>(color.alpha()));
+  paint_.setAlpha(alpha);
+  bool drawShadow = (shadowOffsetX_ != 0 ||
+                     shadowOffsetY_ != 0 ||
+                     shadowBlur_ != 0) &&
+                     shadowColor_.alpha() > 0;
+  if (drawShadow) {
+    // TODO(gram): should we mult shadowColor by globalAlpha?
+    paint_.setLooper(new SkBlurDrawLooper(SkFloatToScalar(shadowBlur_),
+                                          SkFloatToScalar(shadowOffsetX_),
+                                          SkFloatToScalar(shadowOffsetY_),
+                                          shadowColor_.v))->unref();
+  } else {
+    paint_.setLooper(NULL);
+  }
+}
+
 void CanvasState::setGlobalCompositeOperation(const char* op) {
   SkXfermode::Mode mode;
   static const struct CompositOpToXfermodeMode {
@@ -296,3 +335,77 @@
   canvas_->drawBitmapRect(bm, &src, dst);
 }
 
+void CanvasState::SetFillGradient(bool is_radial,
+    double x0, double y0, double r0,
+    double x1, double y1, double r1,
+    int stops, float* positions, char** colors) {
+  if (fillShader_ != NULL) {
+    fillShader_->unref();
+  }
+  if (is_radial) {
+    fillShader_ = CreateRadialGradient(x0, y0, r0, x1, y1, r1,
+        stops, positions, colors);
+  } else {
+    fillShader_ = CreateLinearGradient(x0, y0, x1, y1,
+        stops, positions, colors);
+  }
+  fillShader_->validate();
+}
+
+void CanvasState::SetStrokeGradient(bool is_radial,
+    double x0, double y0, double r0,
+    double x1, double y1, double r1,
+    int stops, float* positions, char** colors) {
+  if (strokeShader_ != NULL) {
+    strokeShader_->unref();
+  }
+  if (is_radial) {
+    strokeShader_ = CreateRadialGradient(x0, y0, r0, x1, y1, r1,
+        stops, positions, colors);
+  } else {
+    strokeShader_ = CreateLinearGradient(x0, y0, x1, y1,
+        stops, positions, colors);
+  }
+  strokeShader_->validate();
+}
+
+SkShader* CanvasState::CreateRadialGradient(
+      double x0, double y0, double r0,
+      double x1, double y1, double r1,
+      int stops, float* positions, char** colors) {
+  SkScalar* p = new SkScalar[stops];
+  SkColor* c = new SkColor[stops];
+  for (int i = 0; i < stops; i++) {
+    p[i] = positions[i];
+    c[i] = GetColor(colors[i]).v;
+  }
+  LOGI("CreateRadialGradient(%f,%f,%f,%f,%f,%f,%d,[%f,%f],[%s,%s]",
+    x0, y0, r0, x1, y1, r1, stops, positions[0], positions[1],
+    colors[0], colors[1]);
+  SkShader* shader = SkGradientShader::CreateTwoPointRadial(
+      SkPoint::Make(x0, y0), r0, SkPoint::Make(x1, y1), r1,
+      c, p, stops, SkShader::kClamp_TileMode);
+  delete[] c;
+  delete[] p;
+  return shader;
+}
+
+SkShader* CanvasState::CreateLinearGradient(
+      double x0, double y0, double x1, double y1,
+      int stops, float* positions, char** colors) {
+  SkScalar* p = new SkScalar[stops];
+  SkColor* c = new SkColor[stops];
+  for (int i = 0; i < stops; i++) {
+    p[i] = positions[i];
+    c[i] = GetColor(colors[i]).v;
+  }
+  SkPoint pts[2];
+  pts[0] = SkPoint::Make(x0, y0);
+  pts[1] = SkPoint::Make(x1, y1);
+  SkShader* shader =  SkGradientShader::CreateLinear(pts, c, p, stops,
+      SkShader::kClamp_TileMode);
+  delete[] c;
+  delete[] p;
+  return shader;
+}
+
diff --git a/runtime/embedders/openglui/common/canvas_state.h b/runtime/embedders/openglui/common/canvas_state.h
index 45581ed..fc0e095 100644
--- a/runtime/embedders/openglui/common/canvas_state.h
+++ b/runtime/embedders/openglui/common/canvas_state.h
@@ -23,6 +23,8 @@
   float* lineDash_;
   int lineDashCount_;
   int lineDashOffset_;
+  SkShader* fillShader_;
+  SkShader* strokeShader_;
 
   SkPath* path_;
   SkCanvas* canvas_;
@@ -41,6 +43,8 @@
       lineDash_(NULL),
       lineDashCount_(0),
       lineDashOffset_(0),
+      fillShader_(NULL),
+      strokeShader_(NULL),
       path_(new SkPath()),
       canvas_(canvas),
       next_(NULL) {
@@ -66,13 +70,19 @@
       lineDash_(NULL),
       lineDashCount_(state.lineDashCount_),
       lineDashOffset_(state.lineDashOffset_),
+      fillShader_(state.fillShader_),
+      strokeShader_(state.strokeShader_),
       path_(new SkPath()),
       canvas_(state.canvas_),
       next_(NULL) {
     setLineDash(state.lineDash_, lineDashCount_);
+    if (fillShader_ != NULL) fillShader_->ref();
+    if (strokeShader_ != NULL) strokeShader_->ref();
   }
 
   ~CanvasState() {
+    if (fillShader_ != NULL) fillShader_->unref();
+    if (strokeShader_ != NULL) strokeShader_->unref();
     delete path_;
     delete[] lineDash_;
   }
@@ -92,21 +102,7 @@
     return new_state;
   }
 
-  inline CanvasState* Restore() {
-    if (next_ != NULL) {
-      // If the state we are popping has a non-empty path,
-      // apply the state's transform to the path, then
-      // add the path to the previous state's path.
-      if (path_->countPoints() > 0) {
-        path_->transform(canvas_->getTotalMatrix());
-        next_->path_->addPath(*path_);
-      }
-      canvas_->restore();
-      return next_;
-    }
-    canvas_->restore();
-    return next_;  // TODO(gram): Should we assert/throw?
-  }
+  CanvasState* Restore();
 
   inline float Radians2Degrees(float angle) {
     return 180.0 * angle / M_PI;
@@ -117,10 +113,18 @@
   }
 
   inline void setFillColor(const char* color) {
+    if (fillShader_ != NULL) {
+      fillShader_->unref();
+      fillShader_ = NULL;
+    }
     fillColor_ = GetColor(color);
   }
 
   inline void setStrokeColor(const char* color) {
+    if (strokeShader_ != NULL) {
+      strokeShader_->unref();
+      strokeShader_ = NULL;
+    }
     strokeColor_ = GetColor(color);
   }
 
@@ -156,26 +160,7 @@
     paint_.setStrokeWidth(w);
   }
 
-  inline void setMode(SkPaint::Style style, ColorRGBA color) {
-    paint_.setStyle(style);
-    paint_.setColor(color.v);
-    uint8_t alpha = static_cast<uint8_t>(
-        globalAlpha_ * static_cast<float>(color.alpha()));
-    paint_.setAlpha(alpha);
-    bool drawShadow = (shadowOffsetX_ != 0 ||
-                       shadowOffsetY_ != 0 ||
-                       shadowBlur_ != 0) &&
-                       shadowColor_.alpha() > 0;
-    if (drawShadow) {
-      // TODO(gram): should we mult shadowColor by globalAlpha?
-      paint_.setLooper(new SkBlurDrawLooper(SkFloatToScalar(shadowBlur_),
-                                            SkFloatToScalar(shadowOffsetX_),
-                                            SkFloatToScalar(shadowOffsetY_),
-                                            shadowColor_.v))->unref();
-    } else {
-      paint_.setLooper(NULL);
-    }
-  }
+  void setMode(SkPaint::Style style, ColorRGBA color, SkShader* shader);
 
   inline void setLineDashEffect() {
     if (lineDashCount_ > 0) {
@@ -225,11 +210,11 @@
   }
 
   inline void setFillMode() {
-    setMode(SkPaint::kFill_Style, fillColor_);
+    setMode(SkPaint::kFill_Style, fillColor_, fillShader_);
   }
 
   inline void setStrokeMode() {
-    setMode(SkPaint::kStroke_Style, strokeColor_);
+    setMode(SkPaint::kStroke_Style, strokeColor_, strokeShader_);
   }
 
   inline void FillRect(float left, float top,
@@ -303,6 +288,24 @@
   inline void Clip() {
     canvas_->clipPath(*path_);
   }
+
+  void SetFillGradient(bool is_radial, double x0, double y0, double r0,
+      double x1, double y1, double r1,
+      int stops, float* positions, char** colors);
+
+  void SetStrokeGradient(bool is_radial, double x0, double y0, double r0,
+      double x1, double y1, double r1,
+      int stops, float* positions, char** colors);
+
+ private:
+  SkShader* CreateRadialGradient(
+      double x0, double y0, double r0,
+      double x1, double y1, double r1,
+      int stops, float* positions, char** colors);
+
+  SkShader* CreateLinearGradient(
+      double x0, double y0, double x1, double y1,
+      int stops, float* positions, char** colors);
 } CanvasState;
 
 #endif  // EMBEDDERS_OPENGLUI_COMMON_CANVAS_STATE_H_
diff --git a/runtime/embedders/openglui/common/dart_host.cc b/runtime/embedders/openglui/common/dart_host.cc
index af886b0..dd2c1cd 100644
--- a/runtime/embedders/openglui/common/dart_host.cc
+++ b/runtime/embedders/openglui/common/dart_host.cc
@@ -7,6 +7,7 @@
 #include <math.h>
 #include <unistd.h>
 
+#include "embedders/openglui/common/image_cache.h"
 #include "embedders/openglui/common/log.h"
 
 DartHost::DartHost(Context *context)
@@ -18,6 +19,7 @@
       has_context_(false),
       started_(false),
       active_(false) {
+  ImageCache::Init(graphics_handler_->resource_path());
 }
 
 DartHost::~DartHost() {
diff --git a/runtime/embedders/openglui/common/extension.cc b/runtime/embedders/openglui/common/extension.cc
index abe627d..eb32a3d 100644
--- a/runtime/embedders/openglui/common/extension.cc
+++ b/runtime/embedders/openglui/common/extension.cc
@@ -9,6 +9,7 @@
 #include <string.h>
 
 #include "embedders/openglui/common/canvas_context.h"
+#include "embedders/openglui/common/image_cache.h"
 #include "embedders/openglui/common/graphics_handler.h"
 #include "embedders/openglui/common/log.h"
 #include "embedders/openglui/common/opengl.h"
@@ -42,11 +43,11 @@
 }
 
 const char* GetArgAsString(Dart_NativeArguments arguments, int idx) {
-  Dart_Handle whatHandle = HandleError(Dart_GetNativeArgument(arguments, idx));
+  Dart_Handle handle = HandleError(Dart_GetNativeArgument(arguments, idx));
   uint8_t* str;
   intptr_t length;
-  HandleError(Dart_StringLength(whatHandle, &length));
-  HandleError(Dart_StringToUTF8(whatHandle, &str, &length));
+  HandleError(Dart_StringLength(handle, &length));
+  HandleError(Dart_StringToUTF8(handle, &str, &length));
   str[length] = 0;
   return  const_cast<const char*>(reinterpret_cast<char*>(str));
 }
@@ -97,52 +98,68 @@
   return false;
 }
 
-GLint* GetArgsAsGLintList(Dart_NativeArguments arguments, int index,
-                          int* len_out) {
-  Dart_Handle argHandle = HandleError(Dart_GetNativeArgument(arguments, index));
+int GetListLength(Dart_NativeArguments arguments, int index,
+    Dart_Handle& argHandle) {
+  argHandle = HandleError(Dart_GetNativeArgument(arguments, index));
   if (Dart_IsList(argHandle)) {
     intptr_t len;
     HandleError(Dart_ListLength(argHandle, &len));
-    GLint* list = new GLint[len];
-    for (int i = 0; i < len; i++) {
-      Dart_Handle vHandle = Dart_ListGetAt(argHandle, i);
-      int64_t v;
-      HandleError(Dart_IntegerToInt64(vHandle, &v));
-      list[i] = v;
-    }
-    *len_out = len;
-    return list;
+    return len;
   }
   LOGI("Argument at index %d has non-List type", index);
   Dart_ThrowException(Dart_NewStringFromCString("List argument expected."));
-  return NULL;
+  return -1;
+}
+
+GLint* GetArgsAsGLintList(Dart_NativeArguments arguments, int index,
+                          int* len_out) {
+  Dart_Handle argHandle;
+  int len = GetListLength(arguments, index, argHandle);
+  if (len < 0) return NULL;
+  GLint* list = new GLint[len];
+  for (int i = 0; i < len; i++) {
+    Dart_Handle vHandle = Dart_ListGetAt(argHandle, i);
+    int64_t v;
+    HandleError(Dart_IntegerToInt64(vHandle, &v));
+    list[i] = v;
+  }
+  *len_out = len;
+  return list;
 }
 
 GLfloat* GetArgsAsFloatList(Dart_NativeArguments arguments, int index,
                             int* len_out) {
-  Dart_Handle locationHandle =
-      HandleError(Dart_GetNativeArgument(arguments, 0));
-  int64_t location;
-  HandleError(Dart_IntegerToInt64(locationHandle, &location));
-
-  Dart_Handle argHandle = HandleError(Dart_GetNativeArgument(arguments, 1));
-
-  if (Dart_IsList(argHandle)) {
-    intptr_t len;
-    HandleError(Dart_ListLength(argHandle, &len));
-    GLfloat* list = new GLfloat[len];
-    for (int i = 0; i < len; i++) {
-      Dart_Handle vHandle = Dart_ListGetAt(argHandle, i);
-      double v;
-      HandleError(Dart_DoubleValue(vHandle, &v));
-      list[i] = v;
-    }
-    *len_out = len;
-    return list;
+  Dart_Handle argHandle;
+  int len = GetListLength(arguments, index, argHandle);
+  if (len < 0) return NULL;
+  GLfloat* list = new GLfloat[len];
+  for (int i = 0; i < len; i++) {
+    Dart_Handle vHandle = Dart_ListGetAt(argHandle, i);
+    double v;
+    HandleError(Dart_DoubleValue(vHandle, &v));
+    list[i] = v;
   }
-  LOGI("Argument at index %d has non-List type", index);
-  Dart_ThrowException(Dart_NewStringFromCString("List argument expected."));
-  return NULL;
+  *len_out = len;
+  return list;
+}
+
+char** GetArgsAsStringList(Dart_NativeArguments arguments, int index,
+                            int* len_out) {
+  Dart_Handle argHandle;
+  int len = GetListLength(arguments, index, argHandle);
+  if (len < 0) return NULL;
+  char** list = new char*[len];
+  for (int i = 0; i < len; i++) {
+    Dart_Handle vHandle = Dart_ListGetAt(argHandle, i);
+    uint8_t* str;
+    intptr_t length;
+    HandleError(Dart_StringLength(vHandle, &length));
+    HandleError(Dart_StringToUTF8(vHandle, &str, &length));
+    str[length] = 0;
+    list[i] = reinterpret_cast<char*>(str);
+  }
+  *len_out = len;
+  return list;
 }
 
 void SetBoolReturnValue(Dart_NativeArguments arguments, bool b) {
@@ -479,9 +496,8 @@
   LOGI("Converted length is %d", static_cast<int>(length[0]));
   str[0][*length] = 0;
 
-  const GLchar* source =
-      const_cast<const GLchar*>(reinterpret_cast<GLchar*>(str[0]));
-  LOGI("Source: %s", source);
+  LOGI("Source: %s",
+      const_cast<const GLchar*>(reinterpret_cast<GLchar*>(str[0])));
   glShaderSource(shader, 1,
       const_cast<const GLchar**>(reinterpret_cast<GLchar**>(str)), NULL);
   CheckGLError("glShaderSource");
@@ -978,12 +994,8 @@
   LOGI("In C2DSetFillStyle");
   Dart_EnterScope();
   int handle = GetArgAsInt(arguments, 0);
-  Dart_Handle whatHandle = HandleError(Dart_GetNativeArgument(arguments, 1));
-  if (Dart_IsString(whatHandle)) {
-    const char* color = GetArgAsString(arguments, 1);
-    Context2D(handle)->setFillColor(color);
-  } else {  // Texture from gradient or image.
-  }
+  const char* color = GetArgAsString(arguments, 1);
+  Context2D(handle)->setFillColor(color);
   Dart_ExitScope();
   LOGI("Out C2DSetFillStyle");
 }
@@ -1371,7 +1383,8 @@
   LOGI("In C2DRestore");
   Dart_EnterScope();
   int handle = GetArgAsInt(arguments, 0);
-  Context2D(handle)->Restore();
+  CanvasContext* context = Context2D(handle);
+  context->Restore();
   Dart_ExitScope();
   LOGI("Out C2DRestore");
 }
@@ -1506,6 +1519,66 @@
   LOGI("Out C2DTranslate");
 }
 
+void C2DSetFillGradient(Dart_NativeArguments arguments) {
+  LOGI("In C2DSetFillGradient");
+  Dart_EnterScope();
+  int handle = GetArgAsInt(arguments, 0);
+  bool is_radial = GetArgAsBool(arguments, 1);
+  double x0 = GetArgAsDouble(arguments, 2);
+  double y0 = GetArgAsDouble(arguments, 3);
+  double r0 = GetArgAsDouble(arguments, 4);
+  double x1 = GetArgAsDouble(arguments, 5);
+  double y1 = GetArgAsDouble(arguments, 6);
+  double r1 = GetArgAsDouble(arguments, 7);
+  int num_positions, num_colors;
+  float* positions = GetArgsAsFloatList(arguments, 8, &num_positions);
+  char** colors = GetArgsAsStringList(arguments, 9, &num_colors);
+  Context2D(handle)->SetFillGradient(is_radial, x0, y0, r0, x1, y1, r1,
+    num_positions, positions, colors);
+  Dart_ExitScope();
+  LOGI("Out C2DSetFillGradient");
+}
+
+void C2DSetStrokeGradient(Dart_NativeArguments arguments) {
+  LOGI("In C2DSetStrokeGradient");
+  Dart_EnterScope();
+  int handle = GetArgAsInt(arguments, 0);
+  bool is_radial = GetArgAsBool(arguments, 1);
+  double x0 = GetArgAsDouble(arguments, 2);
+  double y0 = GetArgAsDouble(arguments, 3);
+  double r0 = GetArgAsDouble(arguments, 4);
+  double x1 = GetArgAsDouble(arguments, 5);
+  double y1 = GetArgAsDouble(arguments, 6);
+  double r1 = GetArgAsDouble(arguments, 7);
+  int num_positions, num_colors;
+  float* positions = GetArgsAsFloatList(arguments, 8, &num_positions);
+  char** colors = GetArgsAsStringList(arguments, 9, &num_colors);
+  Context2D(handle)->SetStrokeGradient(is_radial, x0, y0, r0, x1, y1, r1,
+    num_positions, positions, colors);
+  Dart_ExitScope();
+  LOGI("Out C2DSetStrokeGradient");
+}
+
+void C2DGetImageWidth(Dart_NativeArguments arguments) {
+  LOGI("In C2DGetImageWidth");
+  Dart_EnterScope();
+  const char* src_url = GetArgAsString(arguments, 0);
+  int w = ImageCache::GetWidth(src_url);
+  SetIntReturnValue(arguments, w);
+  Dart_ExitScope();
+  LOGI("Out C2DGetImageWidth");
+}
+
+void C2DGetImageHeight(Dart_NativeArguments arguments) {
+  LOGI("In C2DGetImageHeight");
+  Dart_EnterScope();
+  const char* src_url = GetArgAsString(arguments, 0);
+  int h = ImageCache::GetHeight(src_url);
+  SetIntReturnValue(arguments, h);
+  Dart_ExitScope();
+  LOGI("Out C2DGetImageHeight");
+}
+
 struct FunctionLookup {
   const char* name;
   Dart_NativeFunction function;
@@ -1638,6 +1711,11 @@
     { "C2DStrokeText", C2DStrokeText},
     { "C2DTransform", C2DTransform},
     { "C2DTranslate", C2DTranslate},
+    { "C2DSetFillGradient", C2DSetFillGradient},
+    { "C2DSetStrokeGradient", C2DSetStrokeGradient},
+    { "C2DGetImageWidth", C2DGetImageWidth},
+    { "C2DGetImageHeight", C2DGetImageHeight},
+
     {NULL, NULL}};
 
 Dart_NativeFunction ResolveName(Dart_Handle name, int argc) {
diff --git a/runtime/embedders/openglui/common/gl.dart b/runtime/embedders/openglui/common/gl.dart
index 8b0dc60..084338c 100644
--- a/runtime/embedders/openglui/common/gl.dart
+++ b/runtime/embedders/openglui/common/gl.dart
@@ -19,39 +19,57 @@
 
 class Window {
   static int _nextId = 0;
-  Map<int, RequestAnimationFrameCallback> _callbacks;
+  List _callbacks;
+  List _arguments;
 
-  Window._internal() : _callbacks = new Map();
+  Window._internal() : _callbacks = [], _arguments = [];
+
+  int _scheduleCallback(callback, [argument]) {
+    _callbacks.add(callback);
+    _arguments.add(argument);
+    return _callbacks.length - 1;
+  }
 
   int requestAnimationFrame(RequestAnimationFrameCallback callback) {
-    _callbacks[_nextId++] = callback;
+    return _scheduleCallback(callback,
+        (new DateTime.now()).millisecondsSinceEpoch);
   }
+
   void cancelAnimationFrame(id) {
-    if (_callbacks.containsKey(id)) {
-      _callbacks.remove(id);
-    }
+    _callbacks[id] = null;
+    _arguments[id] = null;
   }
+
   get animationFrame {
     // TODO(gram)
     return null;
   }
 
   void _dispatch() {
-    var when = (new DateTime.now()).millisecondsSinceEpoch;
     // We clear out the callbacks map before calling any callbacks,
     // as they may schedule new callbacks.
     var oldcallbacks = _callbacks;
-    _callbacks = new Map();
-    for (var c in oldcallbacks.values) {
-      c(when);
+    var oldarguments = _arguments;
+    _callbacks = [];
+    _arguments = [];
+    for (var i = 0; i < oldcallbacks.length; i++) {
+      if (oldcallbacks[i] != null) {
+        oldcallbacks[i](oldarguments[i]);
+      }
     }
+    // We could loop around here to handle any callbacks
+    // scheduled in processing the prior ones, but then we
+    // need some other mechanism for trying to get requestAnimationFrame
+    // callbacks at 60fps.
   }
+
+  Map localStorage = {};  // TODO(gram) - Make this persistent.
 }
 
 Window window = new Window._internal();
 
 // The OpenGLUI "equivalent" of HtmlDocument.
-class Document {
+class Document extends Node {
   BodyElement _body;
   get body => _body;
   Document._internal() : _body = new BodyElement();
@@ -61,6 +79,7 @@
 
 // TODO(gram): make private and call from within library context.
 update_() {
+  log("in update");
   window._dispatch();
 }
 
@@ -76,6 +95,7 @@
   static get listeners => _listeners;
 
   bool dispatchEvent(Event event) {
+    var rtn = false;
     if (!_listeners.containsKey(this)) return false;
     var listeners = _listeners[this];
     if (!listeners.containsKey(event.type)) return false;
@@ -83,9 +103,10 @@
     for (var eventListener in eventListeners) {
       if (eventListener != null) {
         eventListener(event);
+        rtn = true;
       }
     }
-    return true;
+    return rtn;
   }
 
   void addListener(String eventType, EventListener handler) {
@@ -126,15 +147,17 @@
   final String type;
   EventTarget target;
   Event(String type) : this.type = type;
+  preventDefault() {}
+  stopPropagation() {}
 }
 
-class KeyEvent extends Event {
+class KeyboardEvent extends Event {
   final bool altKey;
   final bool ctrlKey;
   final bool shiftKey;
   final int keyCode;
 
-  KeyEvent(String type, int keycode, bool alt, bool ctrl, bool shift) 
+  KeyboardEvent(String type, int keycode, bool alt, bool ctrl, bool shift) 
     : super(type),
       keyCode = keycode,
       altKey = alt,
@@ -156,7 +179,6 @@
   }
 }
 
-
 class _EventStreamSubscription<T extends Event> extends StreamSubscription<T> {
   int _pauseCount = 0;
   EventTarget _target;
@@ -256,8 +278,8 @@
 }
 
 class Node extends EventTarget {
-  Stream<KeyEvent> get onKeyDown => new _EventStream(this, 'keydown');
-  Stream<KeyEvent> get onKeyUp => new _EventStream(this, 'keyup');
+  Stream<KeyboardEvent> get onKeyDown => new _EventStream(this, 'keydown');
+  Stream<KeyboardEvent> get onKeyUp => new _EventStream(this, 'keyup');
   Stream<MouseEvent> get onMouseDown => new _EventStream(this, 'mousedown');
   Stream<MouseEvent> get onMouseMove => new _EventStream(this, 'mousemove');
   Stream<MouseEvent> get onMouseUp => new _EventStream(this, 'mouseup');
@@ -272,13 +294,14 @@
   for (var target in document.body.nodes) {
     event.target = target;
     if (target.dispatchEvent(event)) {
-      break;
+      return;
     }
   }
+  document.dispatchEvent(event);
 }
 
 _dispatchKeyEvent(String type, int keyCode, bool alt, bool ctrl, bool shift) {
-  _dispatchEvent(new KeyEvent(type, keyCode, alt, ctrl, shift));
+  _dispatchEvent(new KeyboardEvent(type, keyCode, alt, ctrl, shift));
 }
 
 _dispatchMouseEvent(String type, double x, double y) {
@@ -302,11 +325,8 @@
     _dispatchMouseEvent('mouseup', x, y);
 
 class CanvasElement extends Node {
-  int _height;
-  int _width;
-
-  get height => _height;
-  get width => _width;
+  int height;
+  int width;
 
   CanvasRenderingContext2D _context2d;
   WebGLRenderingContext _context3d;
@@ -318,14 +338,15 @@
 
   CanvasElement({int width, int height})
     : super() {
-    _width = (width == null) ? getDeviceScreenWidth() : width;
-    _height = (height == null) ? getDeviceScreenHeight() : height;
+    this.width = (width == null) ? getDeviceScreenWidth() : width;
+    this.height = (height == null) ? getDeviceScreenHeight() : height;
+    getContext('2d');
   }
 
   CanvasRenderingContext getContext(String contextId) {
     if (contextId == "2d") {
       if (_context2d == null) {
-        _context2d = new CanvasRenderingContext2D(this, _width, _height);
+        _context2d = new CanvasRenderingContext2D(this, width, height);
       }
       return _context2d;
     } else if (contextId == "webgl" || 
@@ -336,6 +357,18 @@
       return _context3d;
     }
   }
+ 
+  String toDataUrl(String type) {
+    // This needs to take the contents of the underlying
+    // canvas painted by the 2d context, give that a unique
+    // URL, and return that. The canvas element should be
+    // reuable afterwards without destroying the previously
+    // rendered data associated with this URL.
+    assert(_context2d != null);
+    var rtn = src;
+    _context2d = null;
+    return rtn;
+  }
 }
 
 class CanvasRenderingContext {
@@ -344,6 +377,21 @@
   CanvasRenderingContext(this.canvas);
 }
 
+class AudioElement {
+  double volume;
+  String _src;
+  get src => _src;
+  set src(String v) {
+    _src = v;
+    _loadSample(v);
+  }
+
+  AudioElement([this._src]);
+  void play() {
+    _playSample(_src);
+  }
+}
+
 // The simplest way to call native code: top-level functions.
 int systemRand() native "SystemRand";
 void systemSrand(int seed) native "SystemSrand";
@@ -528,123 +576,176 @@
 //------------------------------------------------------------------
 // 2D canvas support
 
-int C2DSetWidth(int handle, int width)
-    native "C2DSetWidth";
-int C2DSetHeight(int handle, int height)
-    native "C2DSetHeight";
+int SetWidth(int handle, int width)
+    native "CanvasSetWidth";
+int SetHeight(int handle, int height)
+    native "CanvasSetHeight";
 
-double C2DSetGlobalAlpha(int handle, double globalAlpha)
-    native "C2DSetGlobalAlpha";
-void C2DSetFillStyle(int handle, fs)
-    native "C2DSetFillStyle";
-String C2DSetFont(int handle, String font)
-    native "C2DSetFont";
-void C2DSetGlobalCompositeOperation(int handle, String op)
-    native "C2DSetGlobalCompositeOperation";
-C2DSetLineCap(int handle, String lc)
-    native "C2DSetLineCap";
-C2DSetLineJoin(int handle, String lj)
-    native "C2DSetLineJoin";
-C2DSetLineWidth(int handle, double w)
-    native "C2DSetLineWidth";
-C2DSetMiterLimit(int handle, double limit)
-    native "C2DSetMiterLimit";
-C2DSetShadowBlur(int handle, double blur)
-    native "C2DSetShadowBlur";
-C2DSetShadowColor(int handle, String color)
-    native "C2DSetShadowColor";
-C2DSetShadowOffsetX(int handle, double offset)
-    native "C2DSetShadowOffsetX";
-C2DSetShadowOffsetY(int handle, double offset)
-    native "C2DSetShadowOffsetY";
-void C2DSetStrokeStyle(int handle, ss)
-    native "C2DSetStrokeStyle";
-String C2DSetTextAlign(int handle, String align)
-    native "C2DSetTextAlign";
-String C2DSetTextBaseline(int handle, String baseline)
-    native "C2DSetTextBaseline";
-C2DGetBackingStorePixelRatio(int handle)
-    native "C2DGetBackingStorePixelRatio";
-void C2DSetImageSmoothingEnabled(int handle, bool ise)
-    native "C2DSetImageSmoothingEnabled";    
-void C2DSetLineDash(int handle, List v)
-    native "C2DSetLineDash";
-C2DSetLineDashOffset(int handle, int v)
-    native "C2DSetLineDashOffset";
-void C2DArc(int handle, double x, double y, double radius,
+double SetGlobalAlpha(int handle, double globalAlpha)
+    native "CanvasSetGlobalAlpha";
+void SetFillStyle(int handle, fs)
+    native "CanvasSetFillStyle";
+String SetFont(int handle, String font)
+    native "CanvasSetFont";
+void SetGlobalCompositeOperation(int handle, String op)
+    native "CanvasSetGlobalCompositeOperation";
+SetLineCap(int handle, String lc)
+    native "CanvasSetLineCap";
+SetLineJoin(int handle, String lj)
+    native "CanvasSetLineJoin";
+SetLineWidth(int handle, double w)
+    native "CanvasSetLineWidth";
+SetMiterLimit(int handle, double limit)
+    native "CanvasSetMiterLimit";
+SetShadowBlur(int handle, double blur)
+    native "CanvasSetShadowBlur";
+SetShadowColor(int handle, String color)
+    native "CanvasSetShadowColor";
+SetShadowOffsetX(int handle, double offset)
+    native "CanvasSetShadowOffsetX";
+SetShadowOffsetY(int handle, double offset)
+    native "CanvasSetShadowOffsetY";
+void SetStrokeStyle(int handle, ss)
+    native "CanvasSetStrokeStyle";
+String SetTextAlign(int handle, String align)
+    native "CanvasSetTextAlign";
+String SetTextBaseline(int handle, String baseline)
+    native "CanvasSetTextBaseline";
+GetBackingStorePixelRatio(int handle)
+    native "CanvasGetBackingStorePixelRatio";
+void SetImageSmoothingEnabled(int handle, bool ise)
+    native "CanvasSetImageSmoothingEnabled";    
+void SetLineDash(int handle, List v)
+    native "CanvasSetLineDash";
+SetLineDashOffset(int handle, int v)
+    native "CanvasSetLineDashOffset";
+void Arc(int handle, double x, double y, double radius,
     double startAngle, double endAngle, [bool anticlockwise = false])
-    native "C2DArc";
-void C2DArcTo(int handle, double x1, double y1,
+    native "CanvasArc";
+void ArcTo(int handle, double x1, double y1,
               double x2, double y2, double radius)
-    native "C2DArcTo"; 
-void C2DArcTo2(int handle, double x1, double y1,
+    native "CanvasArcTo"; 
+void ArcTo2(int handle, double x1, double y1,
                double x2, double y2, double radiusX,
     double radiusY, double rotation)
-    native "C2DArcTo2"; 
-void C2DBeginPath(int handle)
-    native "C2DBeginPath";
-void C2DBezierCurveTo(int handle, double cp1x, double cp1y,
+    native "CanvasArcTo2"; 
+void BeginPath(int handle)
+    native "CanvasBeginPath";
+void BezierCurveTo(int handle, double cp1x, double cp1y,
                       double cp2x, double cp2y, double x, double y)
-    native "C2DBezierCurveTo";
-void C2DClearRect(int handle, double x, double y, double w, double h)
-    native "C2DClearRect";
-void C2DClip(int handle)
-    native "C2DClip";
-void C2DClosePath(int handle)
-    native "C2DClosePath";
-ImageData C2DCreateImageDataFromDimensions(int handle, num w, num h)
-    native "C2DCreateImageDataFromDimensions";
-void C2DDrawImage(int handle, String src_url,
+    native "CanvasBezierCurveTo";
+void ClearRect(int handle, double x, double y, double w, double h)
+    native "CanvasClearRect";
+void Clip(int handle)
+    native "CanvasClip";
+void ClosePath(int handle)
+    native "CanvasClosePath";
+ImageData CreateImageDataFromDimensions(int handle, num w, num h)
+    native "CanvasCreateImageDataFromDimensions";
+void DrawImage(int handle, String src_url,
                   int sx, int sy,
                   bool has_src_dimensions, int sw, int sh,
                   int dx, int dy,
                   bool has_dst_dimensions, int dw, int dh)
-    native "C2DDrawImage";
-void C2DFill(int handle)
-    native "C2DFill";
-void C2DFillRect(int handle, double x, double y, double w, double h)
-    native "C2DFillRect";
-void C2DFillText(int handle, String text, double x, double y, double maxWidth)
-    native "C2DFillText";
-ImageData C2DGetImageData(num sx, num sy, num sw, num sh)
-    native "C2DGetImageData";    
-void C2DLineTo(int handle, double x, double y)
-    native "C2DLineTo";
-double C2DMeasureText(int handle, String text)
-    native "C2DMeasureText";
-void C2DMoveTo(int handle, double x, double y)
-    native "C2DMoveTo";
-void C2DPutImageData(int handle, ImageData imagedata, double dx, double dy)
-    native "C2DPutImageData";    
-void C2DQuadraticCurveTo(int handle, double cpx, double cpy, double x, double y)
-    native "C2DQuadraticCurveTo";
-void C2DRect(int handle, double x, double y, double w, double h)
-    native "C2DRect";
-void C2DRestore(int handle)
-    native "C2DRestore";
-void C2DRotate(int handle, double a)
-    native "C2DRotate";
-void C2DSave(int handle)
-    native "C2DSave";
-void C2DScale(int handle, double sx, double sy)
-    native "C2DScale";
-void C2DSetTransform(int handle, double m11, double m12,
+    native "CanvasDrawImage";
+void Fill(int handle)
+    native "CanvasFill";
+void FillRect(int handle, double x, double y, double w, double h)
+    native "CanvasFillRect";
+void FillText(int handle, String text, double x, double y, double maxWidth)
+    native "CanvasFillText";
+ImageData GetImageData(num sx, num sy, num sw, num sh)
+    native "CanvasGetImageData";    
+void LineTo(int handle, double x, double y)
+    native "CanvasLineTo";
+double MeasureText(int handle, String text)
+    native "CanvasMeasureText";
+void MoveTo(int handle, double x, double y)
+    native "CanvasMoveTo";
+void PutImageData(int handle, ImageData imagedata, double dx, double dy)
+    native "CanvasPutImageData";    
+void QuadraticCurveTo(int handle, double cpx, double cpy,
+    double x, double y)
+        native "CanvasQuadraticCurveTo";
+void Rect(int handle, double x, double y, double w, double h)
+    native "CanvasRect";
+void Restore(int handle)
+    native "CanvasRestore";
+void Rotate(int handle, double a)
+    native "CanvasRotate";
+void Save(int handle)
+    native "CanvasSave";
+void Scale(int handle, double sx, double sy)
+    native "CanvasScale";
+void SetTransform(int handle, double m11, double m12,
                      double m21, double m22, double dx, double dy)
-    native "C2DSetTransform";
-void C2DStroke(int handle)
-    native "C2DStroke";
-void C2DStrokeRect(int handle, double x, double y, double w, double h)
-    native "C2DStrokeRect";    
-void C2DStrokeText(int handle, String text, double x, double y, double maxWidth)
-    native "C2DStrokeText";
-void C2DTransform(int handle, double m11, double m12,
+    native "CanvasSetTransform";
+void Stroke(int handle)
+    native "CanvasStroke";
+void StrokeRect(int handle, double x, double y, double w, double h)
+    native "CanvasStrokeRect";    
+void StrokeText(int handle, String text, double x, double y,
+    double maxWidth)
+        native "CanvasStrokeText";
+void Transform(int handle, double m11, double m12,
                   double m21, double m22, double dx, double dy)
-    native "C2DTransform";
-void C2DTranslate(int handle, double x, double y)
-    native "C2DTranslate";
+    native "CanvasTransform";
+void Translate(int handle, double x, double y)
+    native "CanvasTranslate";
 
-void C2DCreateNativeContext(int handle, int width, int height)
-    native "C2DCreateNativeContext";
+void CreateNativeContext(int handle, int width, int height)
+    native "CanvasCreateNativeContext";
+
+void SetFillGradient(int handle, bool isRadial,
+        double x0, double y0, double r0,
+        double x1, double y1, double r1,
+        List<double> positions, List<String> colors)
+    native "CanvasSetFillGradient";
+
+void SetStrokeGradient(int handle, bool isRadial,
+        double x0, double y0, double r0,
+        double x1, double y1, double r1,
+        List<double> positions, List<String> colors)
+    native "CanvasSetStrokeGradient";
+
+int GetImageWidth(String url)
+    native "CanvasGetImageWidth";
+
+int GetImageHeight(String url)
+    native "CanvasGetImageHeight";
+
+class CanvasGradient {
+  num _x0, _y0, _r0 = 0, _x1, _y1, _r1 = 0;
+  bool _isRadial;
+  List<double> _colorStopPositions = [];
+  List<String> _colorStopColors = [];
+
+  void addColorStop(num offset, String color) {
+    _colorStopPositions.add(offset.toDouble());
+    _colorStopColors.add(color);
+  }
+
+  CanvasGradient.linear(this._x0, this._y0, this._x1, this._y1)
+      : _isRadial = false;
+  
+  CanvasGradient.radial(this._x0, this._y0, this._r0,
+                        this._x1, this._y1, this._r1)
+      : _isRadial = true;
+
+  void setAsFillStyle(_handle) {
+    SetFillGradient(_handle, _isRadial,
+        _x0.toDouble(), _y0.toDouble(), _r0.toDouble(),
+        _x1.toDouble(), _y1.toDouble(), _r1.toDouble(),
+        _colorStopPositions, _colorStopColors);
+  }
+
+  void setAsStrokeStyle(_handle) {
+    SetStrokeGradient(_handle, _isRadial,
+        _x0.toDouble(), _y0.toDouble(), _r0.toDouble(),
+        _x1.toDouble(), _y1.toDouble(), _r1.toDouble(),
+        _colorStopPositions, _colorStopColors);
+  }
+}
 
 class ImageElement extends Node {
   Stream<Event> get onLoad => new _EventStream(this, 'load');
@@ -654,23 +755,36 @@
   int _height;
 
   get src => _src;
+
   set src(String v) {
+    log("Set ImageElement src to $v");
     _src = v;
-    var e = new Event('load');
-    e.target = this;
-    dispatchEvent(e);
   }
 
-  get width => _width;
-  set width(int widthp) => _width = widthp;
+  // The onLoad handler may be set after the src, so
+  // we hook into that here...
+  void addListener(String eventType, EventListener handler) {
+    super.addListener(eventType, handler);
+    if (eventType == 'load') {
+      var e = new Event('load');
+      e.target = this;
+      window._scheduleCallback(handler, e);
+    }
+  }
 
-  get height => _height;
+  get width => _width == null ? _width = GetImageWidth(_src) : _width;
+  get height => _height == null ? _height = GetImageHeight(_src) : _height;
+  set width(int widthp) => _width = widthp;
   set height(int heightp) => _height = heightp;
 
   ImageElement({String srcp, int widthp, int heightp})
     : _src = srcp,
       _width = widthp,
       _height = heightp {
+    if (_src != null) {
+      if (_width == null) _width = GetImageWidth(_src);
+      if (_height == null) _height = GetImageHeight(_src);
+    }
   }
 }
 
@@ -690,6 +804,11 @@
   CanvasRenderingContext2D.next_handle = 0;
 }
 
+class Rect {
+  final num top, left, width, height;
+  const Rect(this.left, this.top, this.width, this.height);
+}
+
 class CanvasRenderingContext2D extends CanvasRenderingContext {
   // TODO(gram): We need to support multiple contexts, for cached content
   // prerendered to an offscreen buffer. For this we will use handles, with
@@ -699,20 +818,20 @@
   get handle => _handle;
 
   int _width, _height;
-  set width(int w) { _width = C2DSetWidth(_handle, w); }
+  set width(int w) { _width = SetWidth(_handle, w); }
   get width => _width;
-  set height(int h) { _height = C2DSetHeight(_handle, h); }
+  set height(int h) { _height = SetHeight(_handle, h); }
   get height => _height;
 
   CanvasRenderingContext2D(canvas, width, height) : super(canvas) {
     _width = width;
     _height = height;
-    C2DCreateNativeContext(_handle = next_handle++, width, height);
+    CreateNativeContext(_handle = next_handle++, width, height);
   }
 
   double _alpha = 1.0;
   set globalAlpha(num a) {
-    _alpha = C2DSetGlobalAlpha(_handle, a.toDouble());
+    _alpha = SetGlobalAlpha(_handle, a.toDouble());
   }
   get globalAlpha => _alpha;
 
@@ -720,45 +839,51 @@
   // fillStyle = strokeStyle = "red"
   var _fillStyle = "#000";
   set fillStyle(fs) {
-    C2DSetFillStyle(_handle, _fillStyle = fs);
+    _fillStyle = fs;
+    // TODO(gram): Support for CanvasPattern.
+    if (fs is CanvasGradient) {
+      fs.setAsFillStyle(_handle);
+    } else {
+      SetFillStyle(_handle, fs);
+    }
   }
   get fillStyle => _fillStyle;
 
   String _font = "10px sans-serif";
-  set font(String f) { _font = C2DSetFont(_handle, f); }
+  set font(String f) { _font = SetFont(_handle, f); }
   get font => _font;
 
   String _globalCompositeOperation = "source-over";
   set globalCompositeOperation(String o) =>
-      C2DSetGlobalCompositeOperation(_handle, _globalCompositeOperation = o);
+      SetGlobalCompositeOperation(_handle, _globalCompositeOperation = o);
   get globalCompositeOperation => _globalCompositeOperation;
 
   String _lineCap = "butt"; // "butt", "round", "square"
   get lineCap => _lineCap;
-  set lineCap(String lc) => C2DSetLineCap(_handle, _lineCap = lc);
+  set lineCap(String lc) => SetLineCap(_handle, _lineCap = lc);
 
   int _lineDashOffset = 0;
   get lineDashOffset => _lineDashOffset;
   set lineDashOffset(num v) {
     _lineDashOffset = v.toInt();
-    C2DSetLineDashOffset(_handle, _lineDashOffset);
+    SetLineDashOffset(_handle, _lineDashOffset);
   }
 
   String _lineJoin = "miter"; // "round", "bevel", "miter"
   get lineJoin => _lineJoin;
-  set lineJoin(String lj) =>  C2DSetLineJoin(_handle, _lineJoin = lj);
+  set lineJoin(String lj) =>  SetLineJoin(_handle, _lineJoin = lj);
 
   num _lineWidth = 1.0;
   get lineWidth => _lineWidth;
   set lineWidth(num w) {
-    C2DSetLineWidth(_handle, w.toDouble());
+    SetLineWidth(_handle, w.toDouble());
     _lineWidth = w;
   }
 
   num _miterLimit = 10.0; // (default 10)
   get miterLimit => _miterLimit;
   set miterLimit(num limit) {
-    C2DSetMiterLimit(_handle, limit.toDouble());
+    SetMiterLimit(_handle, limit.toDouble());
     _miterLimit = limit;
   }
 
@@ -766,48 +891,54 @@
   get shadowBlur =>  _shadowBlur;
   set shadowBlur(num blur) {
     _shadowBlur = blur;
-    C2DSetShadowBlur(_handle, blur.toDouble());
+    SetShadowBlur(_handle, blur.toDouble());
   }
 
   String _shadowColor;
   get shadowColor => _shadowColor;
   set shadowColor(String color) =>
-      C2DSetShadowColor(_handle, _shadowColor = color);
+      SetShadowColor(_handle, _shadowColor = color);
   
   num _shadowOffsetX;
   get shadowOffsetX => _shadowOffsetX;
   set shadowOffsetX(num offset) {
     _shadowOffsetX = offset;
-    C2DSetShadowOffsetX(_handle, offset.toDouble());
+    SetShadowOffsetX(_handle, offset.toDouble());
   }
 
   num _shadowOffsetY;
   get shadowOffsetY => _shadowOffsetY;
   set shadowOffsetY(num offset) {
     _shadowOffsetY = offset;
-    C2DSetShadowOffsetY(_handle, offset.toDouble());
+    SetShadowOffsetY(_handle, offset.toDouble());
   }
 
   var _strokeStyle = "#000";
   get strokeStyle => _strokeStyle;
   set strokeStyle(ss) {
-    C2DSetStrokeStyle(_handle, _strokeStyle = ss);
+    _strokeStyle = ss;
+    // TODO(gram): Support for CanvasPattern.
+    if (ss is CanvasGradient) {
+      ss.setAsStrokeStyle(_handle);
+    } else {
+      SetStrokeStyle(_handle, ss);
+    }
   }
 
   String _textAlign = "start";
   get textAlign => _textAlign;
-  set textAlign(String a) { _textAlign = C2DSetTextAlign(_handle, a); }
+  set textAlign(String a) { _textAlign = SetTextAlign(_handle, a); }
 
   String _textBaseline = "alphabetic";
   get textBaseline => _textBaseline;
-  set textBaseline(String b) { _textBaseline = C2DSetTextBaseline(_handle, b); }
+  set textBaseline(String b) { _textBaseline = SetTextBaseline(_handle, b); }
 
-  get webkitBackingStorePixelRatio => C2DGetBackingStorePixelRatio(_handle);
+  get webkitBackingStorePixelRatio => GetBackingStorePixelRatio(_handle);
 
   bool _webkitImageSmoothingEnabled;
   get webkitImageSmoothingEnabled => _webkitImageSmoothingEnabled;
   set webkitImageSmoothingEnabled(bool v) =>
-     C2DSetImageSmoothingEnabled(_webkitImageSmoothingEnabled = v);
+     SetImageSmoothingEnabled(_webkitImageSmoothingEnabled = v);
 
   get webkitLineDash => lineDash;
   set webkitLineDash(List v) => lineDash = v;
@@ -821,7 +952,8 @@
     if (radius < 0) {
       // throw IndexSizeError
     } else {
-      C2DArc(_handle, x.toDouble(), y.toDouble(), radius.toDouble(), a1.toDouble(), a2.toDouble(), anticlockwise);
+      Arc(_handle, x.toDouble(), y.toDouble(), radius.toDouble(),
+          a1.toDouble(), a2.toDouble(), anticlockwise);
     }
   }
 
@@ -830,80 +962,97 @@
   void arcTo(num x1, num y1, num x2, num y2,
     num radiusX, [num radiusY, num rotation]) {
     if (radiusY == null) {
-      C2DArcTo(_handle, x1.toDouble(), y1.toDouble(),
+      ArcTo(_handle, x1.toDouble(), y1.toDouble(),
                         x2.toDouble(), y2.toDouble(), radiusX.toDouble());
     } else {
-      C2DArcTo2(_handle, x1.toDouble(), y1.toDouble(),
+      ArcTo2(_handle, x1.toDouble(), y1.toDouble(),
                          x2.toDouble(), y2.toDouble(),
                          radiusX.toDouble(), radiusY.toDouble(),
                          rotation.toDouble());
     }
   }
 
-  void beginPath() => C2DBeginPath(_handle);
+  void beginPath() => BeginPath(_handle);
 
   void bezierCurveTo(num cp1x, num cp1y, num cp2x, num cp2y,
     num x, num y) =>
-    C2DBezierCurveTo(_handle, cp1x.toDouble(), cp1y.toDouble(),
+    BezierCurveTo(_handle, cp1x.toDouble(), cp1y.toDouble(),
                               cp2x.toDouble(), cp2y.toDouble(),
                               x.toDouble(), y.toDouble());
 
   void clearRect(num x, num y, num w, num h) =>
-    C2DClearRect(_handle, x.toDouble(), y.toDouble(), w.toDouble(), h.toDouble());
+    ClearRect(_handle, x.toDouble(), y.toDouble(),
+        w.toDouble(), h.toDouble());
 
-  void clip() => C2DClip(_handle);
+  void clip() => Clip(_handle);
 
-  void closePath() => C2DClosePath(_handle);
+  void closePath() => ClosePath(_handle);
 
   ImageData createImageData(var imagedata_OR_sw, [num sh = null]) {
     if (sh == null) {
       throw new Exception('Unimplemented createImageData(imagedata)');
     } else {
-      return C2DCreateImageDataFromDimensions(_handle, imagedata_OR_sw, sh);
+      return CreateImageDataFromDimensions(_handle, imagedata_OR_sw, sh);
     }
   }
 
   CanvasGradient createLinearGradient(num x0, num y0, num x1, num y1) {
-    throw new Exception('Unimplemented createLinearGradient');
+    return new CanvasGradient.linear(x0, y0, x1, y1);
   }
 
   CanvasPattern createPattern(canvas_OR_image, String repetitionType) {
     throw new Exception('Unimplemented createPattern');
   }
 
-  CanvasGradient createRadialGradient(num x0, num y0, num x1, num y1, num r1) {
-    throw new Exception('Unimplemented createRadialGradient');
+  CanvasGradient createRadialGradient(num x0, num y0, num r0,
+                                      num x1, num y1, num r1) {
+    return new CanvasGradient.radial(x0, y0, r0, x1, y1, r1);
   }
 
   void drawImage(element, num x1, num y1,
                 [num w1, num h1, num x2, num y2, num w2, num h2]) {
+    if (element == null || element.src == null || element.src.length == 0) {
+      throw "drawImage called with no valid src";
+    } else {
+      log("drawImage ${element.src}");
+    }
     var w = (element.width == null) ? 0 : element.width;
     var h = (element.height == null) ?  0 : element.height;
     if (!?w1) { // drawImage(element, dx, dy)
-      C2DDrawImage(_handle, element.src, 0, 0, false, w, h,
+      DrawImage(_handle, element.src, 0, 0, false, w, h,
                    x1.toInt(), y1.toInt(), false, 0, 0);
     } else if (!?x2) {  // drawImage(element, dx, dy, dw, dh)
-      C2DDrawImage(_handle, element.src, 0, 0, false, w, h,
+      DrawImage(_handle, element.src, 0, 0, false, w, h,
                    x1.toInt(), y1.toInt(), true, w1.toInt(), h1.toInt());
     } else {  // drawImage(image, sx, sy, sw, sh, dx, dy, dw, dh)
-      C2DDrawImage(_handle, element.src, 
+      DrawImage(_handle, element.src, 
                    x1.toInt(), y1.toInt(), true, w1.toInt(), h1.toInt(),
                    x2.toInt(), y2.toInt(), true, w2.toInt(), h2.toInt());
     }
   }
 
-  void fill() => C2DFill(_handle);
+  void drawImageAtScale(element, Rect dest, {Rect sourceRect}) {
+    if (sourceRect == null) {
+      drawImage(element, dest.left, dest.top, dest.width, dest.height);
+    } else {
+      drawImage(element,
+         sourceRect.left, sourceRect.top, sourceRect.width, sourceRect.height,
+         dest.left, dest.top, dest.width, dest.height);
+    }
+  }
+
+  void fill() => Fill(_handle);
 
   void fillRect(num x, num y, num w, num h) =>
-    C2DFillRect(_handle, x.toDouble(), y.toDouble(),
+    FillRect(_handle, x.toDouble(), y.toDouble(),
                          w.toDouble(), h.toDouble());
 
   void fillText(String text, num x, num y, [num maxWidth = -1]) =>
-      C2DFillText(_handle, text, x.toDouble(), y.toDouble(),
+      FillText(_handle, text, x.toDouble(), y.toDouble(),
                                  maxWidth.toDouble());
 
   ImageData getImageData(num sx, num sy, num sw, num sh) =>
-    C2DGetImageData(sx, sy, sw, sh);
+    GetImageData(sx, sy, sw, sh);
 
   List<double> _lineDash = null;
   List<num> getLineDash() {
@@ -916,40 +1065,40 @@
   }
 
   void lineTo(num x, num y) {
-    C2DLineTo(_handle, x.toDouble(), y.toDouble());
+    LineTo(_handle, x.toDouble(), y.toDouble());
   }
 
   TextMetrics measureText(String text) {
-    double w = C2DMeasureText(_handle, text);
+    double w = MeasureText(_handle, text);
     return new TextMetrics(w);
   }
 
   void moveTo(num x, num y) =>
-    C2DMoveTo(_handle, x.toDouble(), y.toDouble());
+    MoveTo(_handle, x.toDouble(), y.toDouble());
 
   void putImageData(ImageData imagedata, num dx, num dy,
                    [num dirtyX, num dirtyY, num dirtyWidth, num dirtyHeight]) {
     if (dirtyX != null || dirtyY != null) {
       throw new Exception('Unimplemented putImageData');
     } else {
-      C2DPutImageData(_handle, imagedata, dx, dy);
+      PutImageData(_handle, imagedata, dx, dy);
     }
   }
 
   void quadraticCurveTo(num cpx, num cpy, num x, num y) =>
-    C2DQuadraticCurveTo(_handle, cpx.toDouble(), cpy.toDouble(),
+    QuadraticCurveTo(_handle, cpx.toDouble(), cpy.toDouble(),
                         x.toDouble(), y.toDouble());
 
   void rect(num x, num y, num w, num h) =>
-    C2DRect(_handle, x.toDouble(), y.toDouble(), w.toDouble(), h.toDouble());
+    Rect(_handle, x.toDouble(), y.toDouble(), w.toDouble(), h.toDouble());
 
-  void restore() => C2DRestore(_handle);
+  void restore() => Restore(_handle);
 
-  void rotate(num angle) => C2DRotate(_handle, angle.toDouble());
+  void rotate(num angle) => Rotate(_handle, angle.toDouble());
 
-  void save() => C2DSave(_handle);
+  void save() => Save(_handle);
 
-  void scale(num x, num y) => C2DScale(_handle, x.toDouble(), y.toDouble());
+  void scale(num x, num y) => Scale(_handle, x.toDouble(), y.toDouble());
 
   void setFillColorHsl(int h, num s, num l, [num a = 1]) {
     throw new Exception('Unimplemented setFillColorHsl');
@@ -984,7 +1133,7 @@
       }
     }
     if (valid) {
-      C2DSetLineDash(_handle, _lineDash = new_dash);
+      SetLineDash(_handle, _lineDash = new_dash);
     }
   }
 
@@ -997,26 +1146,27 @@
   }
 
   void setTransform(num m11, num m12, num m21, num m22, num dx, num dy) =>
-          C2DSetTransform(_handle, m11.toDouble(), m12.toDouble(),
+          SetTransform(_handle, m11.toDouble(), m12.toDouble(),
                                    m21.toDouble(), m22.toDouble(),
                                    dx.toDouble(), dy.toDouble());
 
-  void stroke() => C2DStroke(_handle);
+  void stroke() => Stroke(_handle);
 
   void strokeRect(num x, num y, num w, num h, [num lineWidth]) =>
-    C2DStrokeRect(_handle, x.toDouble(), y.toDouble(), w.toDouble(), h.toDouble());
+    StrokeRect(_handle, x.toDouble(), y.toDouble(),
+        w.toDouble(), h.toDouble());
 
   void strokeText(String text, num x, num y, [num maxWidth = -1]) =>
-      C2DStrokeText(_handle, text, x.toDouble(), y.toDouble(),
+      StrokeText(_handle, text, x.toDouble(), y.toDouble(),
                                  maxWidth.toDouble());
 
   void transform(num m11, num m12, num m21, num m22, num dx, num dy) =>
-          C2DTransform(_handle, m11.toDouble(), m12.toDouble(),
+          Transform(_handle, m11.toDouble(), m12.toDouble(),
                        m21.toDouble(), m22.toDouble(),
                        dx.toDouble(), dy.toDouble());
 
   void translate(num x, num y) =>
-      C2DTranslate(_handle, x.toDouble(), y.toDouble());
+      Translate(_handle, x.toDouble(), y.toDouble());
 
   ImageData webkitGetImageDataHD(num sx, num sy, num sw, num sh) {
     throw new Exception('Unimplemented webkitGetImageDataHD');
@@ -1034,3 +1184,5 @@
   }
 }
 
+int _loadSample(String s) native "LoadSample";
+int _playSample(String s) native "PlaySample";
diff --git a/runtime/embedders/openglui/common/graphics_handler.cc b/runtime/embedders/openglui/common/graphics_handler.cc
index 98d3461..449facb 100644
--- a/runtime/embedders/openglui/common/graphics_handler.cc
+++ b/runtime/embedders/openglui/common/graphics_handler.cc
@@ -109,6 +109,9 @@
 }
 
 int32_t GraphicsHandler::Update() {
+  LOGI("In GraphicsHandler::Update, display_context dirty %s",
+    (display_context == NULL ? "NULL" :
+        (display_context->isDirty() ? "yes":"no")));
   if (display_context != NULL && display_context->isDirty()) {
     LOGI("Flushing display context\n");
     display_context->Flush();
diff --git a/runtime/embedders/openglui/common/image_cache.cc b/runtime/embedders/openglui/common/image_cache.cc
new file mode 100644
index 0000000..f6c1be5
--- /dev/null
+++ b/runtime/embedders/openglui/common/image_cache.cc
@@ -0,0 +1,99 @@
+// Copyright (c) 2012, 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.
+
+#include "embedders/openglui/common/image_cache.h"
+
+#include <ctype.h>
+#include <string.h>
+#include "core/SkStream.h"
+#include "embedders/openglui/common/canvas_context.h"
+
+ImageCache* ImageCache::instance_ = NULL;
+
+extern CanvasContext* Context2D(int handle);
+
+ImageCache::ImageCache(const char* resource_path)
+    : images(), resource_path_(resource_path) {
+}
+
+const SkBitmap* ImageCache::GetImage_(const char* src_url) {
+fprintf(stderr, "ImageCache::GetImage(%s)\n", src_url);
+  if (strncmp(src_url, "context2d://", 12) == 0) {
+    int handle = atoi(src_url + 12);
+    CanvasContext* otherContext = Context2D(handle);
+    return otherContext->GetBitmap();
+  } else if (images.find(src_url) == images.end()) {
+    SkBitmap* bm = Load(src_url);
+    if (bm != NULL) {
+      images[src_url] = bm;
+    }
+    return bm;
+  } else {
+    return images[src_url];
+  }
+}
+
+int ImageCache::GetWidth_(const char* src_url) {
+fprintf(stderr, "ImageCache::GetWidth(%s)\n", src_url);
+  const SkBitmap* image = GetImage(src_url);
+  if (image == NULL) return 0;
+  return image->width();
+}
+
+int ImageCache::GetHeight_(const char* src_url) {
+fprintf(stderr, "ImageCache::GetHeight(%s)\n", src_url);
+  const SkBitmap* image = GetImage(src_url);
+  if (image == NULL) return 0;
+  return image->height();
+}
+
+SkBitmap* ImageCache::Load(const char* src_url) {
+fprintf(stderr, "ImageCache::Load(%s)\n", src_url);
+  SkBitmap *bm = NULL;
+  const char* filepath;
+  if (strncmp(src_url, "file://", 7) == 0) {
+    filepath = src_url + 7;
+  } else {
+    // TODO(gram): We need a way to remap URLs to local file names.
+    // For now I am just using the characters after the last '/'.
+    // Note also that if we want to support URLs and network fetches,
+    // then we introduce more complexity; this can't just be an URL.
+    int pos = strlen(src_url);
+    while (--pos >= 0 && src_url[pos] != '/');
+    filepath = src_url + pos + 1;
+  }
+  char* path;
+  if (filepath[0] == '/') {
+    path = const_cast<char*>(filepath);
+  } else {
+    size_t len1 = strlen(resource_path_);
+    size_t len2 = strlen(filepath);
+    path = new char[len1 + 1 + len2 + 1];
+    strncpy(path, resource_path_, len1+1);
+    strncat(path, "/", 1);
+    strncat(path, filepath, len2);
+  }
+
+  SkFILEStream stream(path);
+  if (stream.isValid()) {
+    // We could use DecodeFile and pass the path, but by creating the
+    // SkStream here we can produce better error log messages.
+    bm = new SkBitmap();
+    if (!SkImageDecoder::DecodeStream(&stream, bm)) {
+      LOGI("Image decode of %s failed", path);
+      return NULL;
+    } else {
+      LOGI("Decode image %s: width=%d,height=%d",
+          path, bm->width(), bm->height());
+    }
+  } else {
+    LOGI("Path %s is invalid", path);
+  }
+
+  if (path != filepath) {
+    delete[] path;
+  }
+  return bm;
+}
+
diff --git a/runtime/embedders/openglui/common/image_cache.h b/runtime/embedders/openglui/common/image_cache.h
new file mode 100644
index 0000000..4aa22f8
--- /dev/null
+++ b/runtime/embedders/openglui/common/image_cache.h
@@ -0,0 +1,58 @@
+// Copyright (c) 2012, 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 EMBEDDERS_OPENGLUI_COMMON_IMAGE_CACHE_H_
+#define EMBEDDERS_OPENGLUI_COMMON_IMAGE_CACHE_H_
+
+#include <map>
+#include <string>
+#include "embedders/openglui/common/log.h"
+#include "embedders/openglui/common/opengl.h"
+#include "embedders/openglui/common/support.h"
+
+class ImageCache {
+ public:
+  static void Init(const char *resource_path) {
+    if (instance_ == NULL) {
+      instance_ = new ImageCache(resource_path);
+    }
+  }
+
+  inline static const SkBitmap* GetImage(const char* src_url) {
+    if (instance_ == NULL) {
+      fprintf(stderr, "GetImage called with no instance_\n");
+      return NULL;
+    }
+    return instance_->GetImage_(src_url);
+  }
+
+  inline static int GetWidth(const char* src_url) {
+    if (instance_ == NULL) {
+      fprintf(stderr, "GetWidth called with no instance_\n");
+      return NULL;
+    }
+    return instance_->GetWidth_(src_url);
+  }
+
+  inline static int GetHeight(const char* src_url) {
+    if (instance_ == NULL) {
+      fprintf(stderr, "GetHeight called with no instance_\n");
+      return NULL;
+    }
+    return instance_->GetHeight_(src_url);
+  }
+
+ private:
+  explicit ImageCache(const char* resource_path);
+  SkBitmap* Load(const char* src_url);
+  const SkBitmap* GetImage_(const char* src_url);
+  int GetWidth_(const char* src_url);
+  int GetHeight_(const char* src_url);
+
+  std::map<std::string, SkBitmap*> images;
+  const char* resource_path_;
+  static ImageCache* instance_;
+};
+
+#endif  // EMBEDDERS_OPENGLUI_COMMON_IMAGE_CACHE_H_
diff --git a/runtime/embedders/openglui/common/input_handler.cc b/runtime/embedders/openglui/common/input_handler.cc
index 7ffef44..7c4c3d2 100644
--- a/runtime/embedders/openglui/common/input_handler.cc
+++ b/runtime/embedders/openglui/common/input_handler.cc
@@ -70,3 +70,7 @@
                               repeat);
 }
 
+void InputHandler::OnAccelerometerEvent(float x, float y, float z) {
+  vm_glue_->OnAccelerometerEvent(x, y, z);
+}
+
diff --git a/runtime/embedders/openglui/common/input_handler.h b/runtime/embedders/openglui/common/input_handler.h
index 521fe65..06d6d0f 100644
--- a/runtime/embedders/openglui/common/input_handler.h
+++ b/runtime/embedders/openglui/common/input_handler.h
@@ -18,6 +18,8 @@
     virtual int OnKeyEvent(KeyEvent event, int64_t when, int32_t key_code,
                            bool isAltKeyDown, bool isCtrlKeyDown,
                            bool isShiftKeyDown, int32_t repeat);
+    virtual void OnAccelerometerEvent(float x, float y, float z);
+
     virtual ~InputHandler() {}
 
   protected:
diff --git a/runtime/embedders/openglui/common/log.h b/runtime/embedders/openglui/common/log.h
index f816792..d74e0f5 100644
--- a/runtime/embedders/openglui/common/log.h
+++ b/runtime/embedders/openglui/common/log.h
@@ -21,5 +21,10 @@
 #include "embedders/openglui/android/android_log.h"
 #endif
 
+#ifndef DEBUG
+#undef LOGI
+#define LOGI(...)
+#endif
+
 #endif  // EMBEDDERS_OPENGLUI_COMMON_LOG_H_
 
diff --git a/runtime/embedders/openglui/common/opengl.h b/runtime/embedders/openglui/common/opengl.h
index 1daaa86..3a41415 100644
--- a/runtime/embedders/openglui/common/opengl.h
+++ b/runtime/embedders/openglui/common/opengl.h
@@ -45,6 +45,7 @@
 #include "core/SkTypeface.h"
 #include "effects/SkBlurDrawLooper.h"
 #include "effects/SkDashPathEffect.h"
+#include "effects/SkGradientShader.h"
 #include "gpu/SkGpuDevice.h"
 #include "gpu/GrContext.h"
 #include "gpu/GrRenderTarget.h"
diff --git a/runtime/embedders/openglui/common/resource.h b/runtime/embedders/openglui/common/resource.h
index 445d2d1..dd07a68 100644
--- a/runtime/embedders/openglui/common/resource.h
+++ b/runtime/embedders/openglui/common/resource.h
@@ -6,14 +6,15 @@
 #define EMBEDDERS_OPENGLUI_COMMON_RESOURCE_H_
 
 #include <stdlib.h>
+#include <string.h>
 
 class Resource {
   public:
     explicit Resource(const char* path)
-        :  path_(path),
-           descriptor_(-1),
+        :  descriptor_(-1),
            start_(0),
            length_(-1) {
+      path_ = strdup(path);
     }
 
     const char* path() {
@@ -44,10 +45,11 @@
     }
 
     virtual ~Resource() {
+      free(path_);
     }
 
   protected:
-    const char* path_;
+    char* path_;
     int32_t descriptor_;
     off_t start_;
     off_t length_;
diff --git a/runtime/embedders/openglui/common/sample.h b/runtime/embedders/openglui/common/sample.h
index d88f52f..5fc4239 100644
--- a/runtime/embedders/openglui/common/sample.h
+++ b/runtime/embedders/openglui/common/sample.h
@@ -7,20 +7,23 @@
 
 #include "embedders/openglui/common/resource.h"
 
+extern Resource* MakePlatformResource(const char *path);
+
 class Sample {
   public:
     explicit Sample(const char* path)
-        : resource_(path),
-          buffer_(NULL),
+        : buffer_(NULL),
           length_(0) {
+      resource_ = MakePlatformResource(path);
     }
 
     ~Sample() {
       Unload();
+      delete resource_;
     }
 
     const char* path() {
-      return resource_.path();
+      return resource_->path();
     }
 
     uint8_t* buffer() {
@@ -33,10 +36,10 @@
 
     int32_t Load() {
       int32_t rtn = -1;
-      if (resource_.Open() == 0) {
-        buffer_ = new uint8_t[length_ = resource_.length()];
-        rtn = resource_.Read(buffer_, length_);
-        resource_.Close();
+      if (resource_->Open() == 0) {
+        buffer_ = new uint8_t[length_ = resource_->length()];
+        rtn = resource_->Read(buffer_, length_);
+        resource_->Close();
       }
       return rtn;
     }
@@ -51,7 +54,7 @@
 
   private:
     friend class SoundService;
-    Resource resource_;
+    Resource* resource_;
     uint8_t* buffer_;
     off_t length_;
 };
diff --git a/runtime/embedders/openglui/common/sound_handler.cc b/runtime/embedders/openglui/common/sound_handler.cc
index 06c902f..8af2379 100644
--- a/runtime/embedders/openglui/common/sound_handler.cc
+++ b/runtime/embedders/openglui/common/sound_handler.cc
@@ -8,10 +8,15 @@
 
 #include "embedders/openglui/common/log.h"
 
-SoundHandler* SoundHandler::instance_ = NULL;
+// TODO(gram): Clean up this instance pointer; either make the class
+// a proper singleton or provide a cleaner way for the static functions
+// at the end to access it (those functions are the hooks into the Dart
+// native extension).
+SoundHandler* instance_ = NULL;
 
 SoundHandler::SoundHandler()
     : samples_() {
+  instance_ = this;
 }
 
 Sample* SoundHandler::GetSample(const char* path) {
@@ -20,6 +25,7 @@
        ++sp) {
     Sample* sample = (*sp);
     if (strcmp(sample->path(), path) == 0) {
+      LOGI("Returning cached sample %s", path);
       return sample;
     }
   }
@@ -30,22 +36,23 @@
     return NULL;
   }
   samples_.push_back(sample);
+  LOGI("Adding sample %s to cache", path);
   return sample;
 }
 
 int32_t PlayBackgroundSound(const char* path) {
-  return SoundHandler::instance()->PlayBackground(path);
+  return instance_->PlayBackground(path);
 }
 
 void StopBackgroundSound() {
-  SoundHandler::instance()->StopBackground();
+  instance_->StopBackground();
 }
 
 int32_t LoadSoundSample(const char* path) {
-  return SoundHandler::instance()->LoadSample(path);
+  return instance_->LoadSample(path);
 }
 
 int32_t PlaySoundSample(const char* path) {
-  return SoundHandler::instance()->PlaySample(path);
+  return instance_->PlaySample(path);
 }
 
diff --git a/runtime/embedders/openglui/common/sound_handler.h b/runtime/embedders/openglui/common/sound_handler.h
index 0110db9..61090a7 100644
--- a/runtime/embedders/openglui/common/sound_handler.h
+++ b/runtime/embedders/openglui/common/sound_handler.h
@@ -45,11 +45,8 @@
     }
 
     virtual int32_t PlaySample(const char* path) {
-      return 0;
-    }
-
-    static SoundHandler* instance() {
-      return instance_;
+      // Just do a load so we can get logging.
+      return (GetSample(path) == NULL) ? -1 : 0;
     }
 
   protected:
@@ -58,8 +55,6 @@
     Sample* GetSample(const char* path);
 
     samples_t samples_;
-
-    static SoundHandler* instance_;
 };
 
 int32_t PlayBackgroundSound(const char* path);
diff --git a/runtime/embedders/openglui/common/vm_glue.cc b/runtime/embedders/openglui/common/vm_glue.cc
index 1fde06c..4b7bccd 100644
--- a/runtime/embedders/openglui/common/vm_glue.cc
+++ b/runtime/embedders/openglui/common/vm_glue.cc
@@ -27,7 +27,11 @@
                const char* main_script)
     : surface_(surface),
       isolate_(NULL),
-      initialized_script_(false) {
+      initialized_script_(false),
+      x_(0.0),
+      y_(0.0),
+      z_(0.0),
+      accelerometer_changed_(false) {
   LOGI("Creating VMGlue");
   if (main_script == NULL) {
     main_script = "main.dart";
@@ -235,11 +239,25 @@
 
 int VMGlue::CallUpdate() {
   if (initialized_script_) {
+    // If the accelerometer has changed, first do that
+    // event.
     Dart_EnterIsolate(isolate_);
+    if (accelerometer_changed_) {
+      Dart_Handle args[3];
+      LOGI("Invoking onAccelerometer(%f,%f,%f)", x_, y_, z_);
+      Dart_EnterScope();
+      args[0] = CheckError(Dart_NewDouble(x_));
+      args[1] = CheckError(Dart_NewDouble(y_));
+      args[2] = CheckError(Dart_NewDouble(z_));
+      Invoke("onAccelerometer", 3, args, false);
+      Dart_ExitScope();
+      accelerometer_changed_ = false;
+    }
     Dart_EnterScope();
     int rtn = Invoke("update_", 0, 0);
     Dart_ExitScope();
     Dart_ExitIsolate();
+    LOGI("Invoke update_ returns %d", rtn);
     return rtn;
   }
   return -1;
@@ -280,7 +298,7 @@
                        bool isAltKeyDown, bool isCtrlKeyDown,
                        bool isShiftKeyDown, int32_t repeat) {
   if (initialized_script_) {
-    LOGI("Invoking %s", function);
+    LOGI("Invoking %s(_,%d,...)", function, key_code);
     Dart_EnterIsolate(isolate_);
     Dart_EnterScope();
     Dart_Handle args[6];
diff --git a/runtime/embedders/openglui/common/vm_glue.h b/runtime/embedders/openglui/common/vm_glue.h
index 76e2270..cf7788f 100644
--- a/runtime/embedders/openglui/common/vm_glue.h
+++ b/runtime/embedders/openglui/common/vm_glue.h
@@ -32,6 +32,15 @@
   int OnKeyEvent(const char* funtion, int64_t when, int32_t key_code,
                  bool isAltKeyDown, bool isCtrlKeyDown, bool isShiftKeyDown,
                  int32_t repeat);
+  inline void OnAccelerometerEvent(float x, float y, float z) {
+    if (x != x_ || y != y_ || z != z_) {
+      x_ = x;
+      y_ = y;
+      z_ = z;
+      accelerometer_changed_ = true;
+    }
+  }
+
   void FinishMainIsolate();
 
  private:
@@ -54,11 +63,13 @@
   static void ShutdownIsolate(void* callback_data);
 
   static bool initialized_vm_;
+  static char* extension_script_;
   ISized* surface_;
   Dart_Isolate isolate_;
   bool initialized_script_;
   char* main_script_;
-  static char* extension_script_;
+  float x_, y_, z_;  // Last values from accelerometer.
+  bool accelerometer_changed_;
 };
 
 #endif  // EMBEDDERS_OPENGLUI_COMMON_VM_GLUE_H_
diff --git a/runtime/embedders/openglui/emulator/emulator_embedder.cc b/runtime/embedders/openglui/emulator/emulator_embedder.cc
index 831f1e8..904a60f 100644
--- a/runtime/embedders/openglui/emulator/emulator_embedder.cc
+++ b/runtime/embedders/openglui/emulator/emulator_embedder.cc
@@ -6,6 +6,7 @@
 
 #include <string.h>
 #include <sys/time.h>
+#include <time.h>
 #include "embedders/openglui/common/canvas_context.h"
 #include "embedders/openglui/common/context.h"
 #include "embedders/openglui/common/dart_host.h"
@@ -15,6 +16,7 @@
 #include "embedders/openglui/common/sound_handler.h"
 #include "embedders/openglui/common/vm_glue.h"
 #include "embedders/openglui/emulator/emulator_graphics_handler.h"
+#include "embedders/openglui/emulator/emulator_resource.h"
 
 InputHandler* input_handler_ptr;
 LifeCycleHandler* lifecycle_handler_ptr;
@@ -22,17 +24,21 @@
 struct timeval tvStart;
 void tick(int data);
 
+Resource* MakePlatformResource(const char *path) {
+  return new EmulatorResource(path);
+}
+
 void display() {
   // Get number of msecs since last call.
   struct timeval tvEnd;
   gettimeofday(&tvEnd, NULL);
-  uint64_t elapsed = (tvEnd.tv_usec + 1000000 * tvEnd.tv_sec) -
-                 (tvStart.tv_usec + 1000000 * tvStart.tv_sec);
+  uint64_t now = (tvEnd.tv_usec + 1000000 * tvEnd.tv_sec);
 
   if (lifecycle_handler_ptr->OnStep() != 0) {
     exit(-1);
   }
   // Schedule next call, trying to aim for 60fps.
+  uint64_t elapsed = now - (tvStart.tv_usec + 1000000 * tvStart.tv_sec);
   int delay = 1000 / 60 - (elapsed / 1000);
   if (delay < 0) delay = 0;
   tvStart = tvEnd;
@@ -55,16 +61,16 @@
 void keyboard(unsigned char key, int x, int y) {
   input_handler_ptr->OnKeyEvent(kKeyDown, time(0), key, false, false, false, 0);
   input_handler_ptr->OnKeyEvent(kKeyUp, time(0), key, false, false, false, 0);
-  if (key == 27) {
+  if (key == 'Q') {
     lifecycle_handler_ptr->Pause();
     lifecycle_handler_ptr->Deactivate();
     lifecycle_handler_ptr->FreeAllResources();
     exit(0);
-  } else if (key == '0') {
+  } else if (key == 'S') {
     LOGI("Simulating suspend");
     lifecycle_handler_ptr->Pause();
     lifecycle_handler_ptr->Deactivate();
-  } else if (key == '1') {
+  } else if (key == 'R') {
     LOGI("Simulating resume");
     lifecycle_handler_ptr->Activate();
     lifecycle_handler_ptr->Resume();
diff --git a/runtime/embedders/openglui/emulator/emulator_graphics_handler.cc b/runtime/embedders/openglui/emulator/emulator_graphics_handler.cc
index 451e909..606dc76 100644
--- a/runtime/embedders/openglui/emulator/emulator_graphics_handler.cc
+++ b/runtime/embedders/openglui/emulator/emulator_graphics_handler.cc
@@ -11,7 +11,8 @@
                                                  char** argv)
   : GraphicsHandler(".") {
   glutInit(&argc, argv);
-  SetViewport(0, 0, 480, 800);
+  width_ = 800;
+  height_ = 480;
   for (int i = 1; i < argc; i++) {
     if (argv[i][0] == '-') {
       int next_arg = i + 1;
@@ -22,6 +23,7 @@
       }
     }
   }
+  SetViewport(0, 0, width_, height_);
   glutInitWindowSize(width_, height_);
   glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH | GLUT_STENCIL);
   glutCreateWindow("Dart");
diff --git a/runtime/embedders/openglui/emulator/emulator_resource.h b/runtime/embedders/openglui/emulator/emulator_resource.h
index bceebd6..fc54f8a 100644
--- a/runtime/embedders/openglui/emulator/emulator_resource.h
+++ b/runtime/embedders/openglui/emulator/emulator_resource.h
@@ -8,6 +8,7 @@
 #include <fcntl.h>
 #include <sys/stat.h>
 #include <sys/types.h>
+#include <unistd.h>
 
 #include "embedders/openglui/common/log.h"
 #include "embedders/openglui/common/resource.h"
@@ -15,7 +16,7 @@
 class EmulatorResource : public Resource {
   public:
     explicit EmulatorResource(const char* path)
-      : base(path),
+      : Resource(path),
         fd_(-1) {
     }
 
@@ -28,8 +29,8 @@
 
     off_t length() {
       if (length_ < 0) {
-        length_ = lseek(fd), 0, SEEK_END);
-        lseek(fd), 0, SEEK_START);
+        length_ = lseek(fd_, 0, SEEK_END);
+        lseek(fd_, 0, SEEK_SET);
       }
       return length_;
     }
@@ -51,7 +52,7 @@
     }
 
     int32_t Read(void* buffer, size_t count) {
-      size_t actual = read(asset_, buffer, count);
+      size_t actual = read(fd_, buffer, count);
       return (actual == count) ? 0 : -1;
     }
 
diff --git a/runtime/embedders/openglui/openglui_embedder.gypi b/runtime/embedders/openglui/openglui_embedder.gypi
index a9ca5dd..2893fbe 100644
--- a/runtime/embedders/openglui/openglui_embedder.gypi
+++ b/runtime/embedders/openglui/openglui_embedder.gypi
@@ -3,6 +3,13 @@
 # BSD-style license that can be found in the LICENSE file.
 
 {
+  # TODO(gram) : figure out how to make this be autoconfigured. 
+  # I've tried a bunch of things with no success yet.
+  'variables': {
+    'skia_build_flag' : '--release',
+    'skia_libs_location_android': '-Lthird_party/skia/trunk/out/config/android-x86/Release/obj.target/gyp', 
+    'skia_libs_location_desktop': '-Lthird_party/skia/trunk/out/Release', 
+  },
   'conditions': [
     ['OS=="android"',
       {
@@ -66,6 +73,8 @@
               'common/extension.h',
               'common/graphics_handler.cc',
               'common/graphics_handler.h',
+              'common/image_cache.cc',
+              'common/image_cache.h',
               'common/input_handler.cc',
               'common/input_handler.h',
               'common/isized.h',
@@ -92,10 +101,9 @@
                 # real libraries we'll just point to the location of the 'thin'
                 # libraries used by the Skia build for now.
                 # TODO(gram): We need to support debug vs release modes.
-                '-Lthird_party/skia/trunk/out/config/android-x86/Debug/obj.target/gyp', 
+                '<(skia_libs_location_android)',
                 '-z',
                 'muldefs',
-                '-g'
               ],
               'ldflags!': [
                 '-Wl,--exclude-libs=ALL,-shared',
@@ -153,6 +161,7 @@
                 'action': [
                   'embedders/openglui/build_skia.sh',
                   '--android',
+                  '<(skia_build_flag)',
                   '..'
                 ],
                 'message': 'Building Skia.'
@@ -207,6 +216,8 @@
               'common/extension.h',
               'common/graphics_handler.cc',
               'common/graphics_handler.h',
+              'common/image_cache.cc',
+              'common/image_cache.h',
               'common/input_handler.cc',
               'common/input_handler.h',
               'common/isized.h',
@@ -234,8 +245,7 @@
             'link_settings': {
               'ldflags': [
                 '-Wall',
-                '-g',
-                '-Lthird_party/skia/trunk/out/Debug', 
+                '<(skia_libs_location_desktop)',
                 '-Wl,--start-group',
                 '-lskia_effects',
                 '-lskia_images',
@@ -279,6 +289,7 @@
                 ],
                 'action': [
                   'embedders/openglui/build_skia.sh',
+                  '<(skia_build_flag)',
                   '..'
                 ],
                 'message': 'Building Skia.'
diff --git a/runtime/lib/byte_array.cc b/runtime/lib/byte_array.cc
index 4a806a6..a96d211 100644
--- a/runtime/lib/byte_array.cc
+++ b/runtime/lib/byte_array.cc
@@ -251,16 +251,6 @@
 }
 
 
-DEFINE_NATIVE_ENTRY(ByteArray_getFloat32x4, 2) {
-  UNALIGNED_GETTER(ByteArray, Float32x4, simd128_value_t);
-}
-
-
-DEFINE_NATIVE_ENTRY(ByteArray_setFloat32x4, 3) {
-  UNALIGNED_SETTER(ByteArray, Float32x4, value, simd128_value_t);
-}
-
-
 DEFINE_NATIVE_ENTRY(ByteArray_getFloat32, 2) {
   UNALIGNED_GETTER(ByteArray, Double, float);
 }
@@ -606,39 +596,6 @@
   SETTER_UINT64(Uint64Array);
 }
 
-// Float32x4Array
-
-DEFINE_NATIVE_ENTRY(Float32x4Array_new, 1) {
-  GET_NON_NULL_NATIVE_ARGUMENT(Smi, length, arguments->NativeArgAt(0));
-  intptr_t len = length.Value();
-  LengthCheck(len, Float32x4Array::kMaxElements);
-  return Float32x4Array::New(len);
-}
-
-
-DEFINE_NATIVE_ENTRY(Float32x4List_newTransferable, 1) {
-  const int kAlignment = 16;
-  GET_NON_NULL_NATIVE_ARGUMENT(Smi, length, arguments->NativeArgAt(0));
-  intptr_t len = length.Value();
-  LengthCheck(len, Float32x4Array::kMaxElements);
-  simd128_value_t* bytes =
-      OS::AllocateAlignedArray<simd128_value_t>(len, kAlignment);
-  const ExternalFloat32x4Array& obj =
-      ExternalFloat32x4Array::Handle(ExternalFloat32x4Array::New(bytes, len));
-  obj.AddFinalizer(bytes, PeerFinalizer);
-  return obj.raw();
-}
-
-
-DEFINE_NATIVE_ENTRY(Float32x4Array_getIndexed, 2) {
-  GETTER(Float32x4Array, Float32x4, simd128_value_t);
-}
-
-
-DEFINE_NATIVE_ENTRY(Float32x4Array_setIndexed, 3) {
-  SETTER(Float32x4Array, Float32x4, value, simd128_value_t);
-}
-
 
 // Float32Array
 
@@ -814,18 +771,6 @@
 }
 
 
-// ExternalFloat32x4Array
-
-DEFINE_NATIVE_ENTRY(ExternalFloat32x4Array_getIndexed, 2) {
-  GETTER(ExternalFloat32x4Array, Float32x4, simd128_value_t);
-}
-
-
-DEFINE_NATIVE_ENTRY(ExternalFloat32x4Array_setIndexed, 3) {
-  SETTER(ExternalFloat32x4Array, Float32x4, value, simd128_value_t);
-}
-
-
 // ExternalFloat32Array
 
 DEFINE_NATIVE_ENTRY(ExternalFloat32Array_getIndexed, 2) {
diff --git a/runtime/lib/byte_array.dart b/runtime/lib/byte_array.dart
index d2e1ec0..5dcf1dc 100644
--- a/runtime/lib/byte_array.dart
+++ b/runtime/lib/byte_array.dart
@@ -445,10 +445,6 @@
   int _getUint64(int byteOffset) native "ByteArray_getUint64";
   int _setUint64(int byteOffset, int value) native "ByteArray_setUint64";
 
-  Float32x4 _getFloat32x4(int byteOffset) native "ByteArray_getFloat32x4";
-  int _setFloat32x4(int byteOffset, Float32x4 value)
-      native "ByteArray_setFloat32x4";
-
   double _getFloat32(int byteOffset) native "ByteArray_getFloat32";
   int _setFloat32(int byteOffset, double value) native "ByteArray_setFloat32";
 
@@ -2010,13 +2006,6 @@
     return _array._setUint64(_offset + byteOffset, value);
   }
 
-  Float32x4 getFloat32x4(int byteOffset) {
-    return _array._getFloat32x4(_offset + byteOffset);
-  }
-  int setFloat32x4(int byteOffset, Float32x4 value) {
-    return _array._setFloat32x4(_offset + byteOffset, value);
-  }
-
   double getFloat32(int byteOffset) {
     return _array._getFloat32(_offset + byteOffset);
   }
diff --git a/runtime/lib/lib_sources.gypi b/runtime/lib/lib_sources.gypi
index 27e36a9..d3efd48 100644
--- a/runtime/lib/lib_sources.gypi
+++ b/runtime/lib/lib_sources.gypi
@@ -48,7 +48,6 @@
     'stopwatch_patch.dart',
     'stopwatch.cc',
     'string.cc',
-    'string_base.dart',
     'string_patch.dart',
     'string_buffer_patch.dart',
     'type_patch.dart',
diff --git a/runtime/lib/scalarlist_sources.gypi b/runtime/lib/scalarlist_sources.gypi
index 678ceb6..cb7c3dd 100644
--- a/runtime/lib/scalarlist_sources.gypi
+++ b/runtime/lib/scalarlist_sources.gypi
@@ -8,8 +8,6 @@
   'sources': [
     'byte_array.cc',
     'byte_array.dart',
-    'simd128.cc',
-    'simd128.dart',
   ],
 }
 
diff --git a/runtime/lib/simd128.dart b/runtime/lib/simd128.dart
deleted file mode 100644
index ca3f587..0000000
--- a/runtime/lib/simd128.dart
+++ /dev/null
@@ -1,782 +0,0 @@
-// Copyright (c) 2013, 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.
-
-patch class Float32x4 {
-  /* patch */ factory Float32x4(double x, double y, double z, double w) {
-    return new _Float32x4(x, y, z, w);
-  }
-  /* patch */ factory Float32x4.zero() {
-    return new _Float32x4.zero();
-  }
-}
-
-patch class Uint32x4 {
-  /* patch */ factory Uint32x4(int x, int y, int z, int w) {
-    return new _Uint32x4(x, y, z, w);
-  }
-  /* patch */ factory Uint32x4.bool(bool x, bool y, bool z, bool w) {
-    return new _Uint32x4.bool(x, y, z, w);
-  }
-}
-
-
-patch class Float32x4List {
-  /* patch */ factory Float32x4List(int length) {
-    return new _Float32x4Array(length);
-  }
-
-  /* patch */ factory Float32x4List.transferable(int length) {
-    return _newTransferable(length);
-  }
-
-  /* patch */ factory Float32x4List.view(ByteArray array,
-                                                [int start = 0, int length]) {
-    return new _Float32x4ArrayView(array, start, length);
-  }
-
-  static _ExternalFloat32x4Array _newTransferable(int length)
-      native "Float32x4List_newTransferable";
-}
-
-
-// Expose native square root.
-double _sqrt(double x) native "Math_sqrt";
-class _Float32x4Dart implements Float32x4 {
-  final Float32List _storage = new Float32List(4);
-  _Float32x4Dart.empty() {
-  }
-  _Float32x4Dart.copy(Float32List other) {
-    _storage[0] = other._storage[0];
-    _storage[1] = other._storage[1];
-    _storage[2] = other._storage[2];
-    _storage[3] = other._storage[3];
-  }
-  factory _Float32x4Dart(double x, double y, double z, double w) {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = x;
-    instance._storage[1] = y;
-    instance._storage[2] = z;
-    instance._storage[3] = w;
-    return instance;
-  }
-  factory _Float32x4Dart.zero() {
-    var instance = new _Float32x4Dart.empty();
-    return instance;
-  }
-  Float32x4 operator +(Float32x4 other) {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = _storage[0] + other._storage[0];
-    instance._storage[1] = _storage[1] + other._storage[1];
-    instance._storage[2] = _storage[2] + other._storage[2];
-    instance._storage[3] = _storage[3] + other._storage[3];
-    return instance;
-  }
-  Float32x4 operator -() {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = -_storage[0];
-    instance._storage[1] = -_storage[1];
-    instance._storage[2] = -_storage[2];
-    instance._storage[3] = -_storage[3];
-    return instance;
-  }
-  Float32x4 operator -(Float32x4 other) {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = _storage[0] - other._storage[0];
-    instance._storage[1] = _storage[1] - other._storage[1];
-    instance._storage[2] = _storage[2] - other._storage[2];
-    instance._storage[3] = _storage[3] - other._storage[3];
-    return instance;
-  }
-  Float32x4 operator *(Float32x4 other) {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = _storage[0] * other._storage[0];
-    instance._storage[1] = _storage[1] * other._storage[1];
-    instance._storage[2] = _storage[2] * other._storage[2];
-    instance._storage[3] = _storage[3] * other._storage[3];
-    return instance;
-  }
-  Float32x4 operator /(Float32x4 other) {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = _storage[0] / other._storage[0];
-    instance._storage[1] = _storage[1] / other._storage[1];
-    instance._storage[2] = _storage[2] / other._storage[2];
-    instance._storage[3] = _storage[3] / other._storage[3];
-    return instance;
-  }
-  Uint32x4 lessThan(Float32x4 other) {
-    bool _x = _storage[0] < other._storage[0];
-    bool _y = _storage[1] < other._storage[1];
-    bool _z = _storage[2] < other._storage[2];
-    bool _w = _storage[3] < other._storage[3];
-    return new Uint32x4.bool(_x, _y, _z, _w);
-  }
-  Uint32x4 lessThanOrEqual(Float32x4 other) {
-    bool _x = _storage[0] <= other._storage[0];
-    bool _y = _storage[1] <= other._storage[1];
-    bool _z = _storage[2] <= other._storage[2];
-    bool _w = _storage[3] <= other._storage[3];
-    return new Uint32x4.bool(_x, _y, _z, _w);
-  }
-  Uint32x4 greaterThan(Float32x4 other) {
-    bool _x = _storage[0] > other._storage[0];
-    bool _y = _storage[1] > other._storage[1];
-    bool _z = _storage[2] > other._storage[2];
-    bool _w = _storage[3] > other._storage[3];
-    return new Uint32x4.bool(_x, _y, _z, _w);
-  }
-  Uint32x4 greaterThanOrEqual(Float32x4 other) {
-    bool _x = _storage[0] >= other._storage[0];
-    bool _y = _storage[1] >= other._storage[1];
-    bool _z = _storage[2] >= other._storage[2];
-    bool _w = _storage[3] >= other._storage[3];
-    return new Uint32x4.bool(_x, _y, _z, _w);
-  }
-  Uint32x4 equal(Float32x4 other) {
-    bool _x = _storage[0] == other._storage[0];
-    bool _y = _storage[1] == other._storage[1];
-    bool _z = _storage[2] == other._storage[2];
-    bool _w = _storage[3] == other._storage[3];
-    return new Uint32x4.bool(_x, _y, _z, _w);
-  }
-  Uint32x4 notEqual(Float32x4 other) {
-    bool _x = _storage[0] != other._storage[0];
-    bool _y = _storage[1] != other._storage[1];
-    bool _z = _storage[2] != other._storage[2];
-    bool _w = _storage[3] != other._storage[3];
-    return new Uint32x4.bool(_x, _y, _z, _w);
-  }
-  Float32x4 scale(double s) {
-    var instance = new _Float32x4Dart.copy(this);
-    instance._storage[0] *= s;
-    instance._storage[1] *= s;
-    instance._storage[2] *= s;
-    instance._storage[3] *= s;
-    return instance;
-  }
-  Float32x4 abs() {
-    var instance = new _Float32x4Dart.copy(this);
-    instance._storage[0] = instance._storage[0].abs();
-    instance._storage[1] = instance._storage[1].abs();
-    instance._storage[2] = instance._storage[2].abs();
-    instance._storage[3] = instance._storage[3].abs();
-    return instance;
-  }
-  Float32x4 clamp(Float32x4 lowerLimit,
-                         Float32x4 upperLimit) {
-    var instance = new _Float32x4Dart.copy(this);
-    if (instance._storage[0] > upperLimit._storage[0]) {
-      instance._storage[0] = upperLimit._storage[0];
-    }
-    if (instance._storage[1] > upperLimit._storage[1]) {
-      instance._storage[1] = upperLimit._storage[1];
-    }
-    if (instance._storage[2] > upperLimit._storage[2]) {
-      instance._storage[2] = upperLimit._storage[2];
-    }
-    if (instance._storage[3] > upperLimit._storage[3]) {
-      instance._storage[3] = upperLimit._storage[3];
-    }
-    if (instance._storage[0] < lowerLimit._storage[0]) {
-      instance._storage[0] = lowerLimit._storage[0];
-    }
-    if (instance._storage[1] < lowerLimit._storage[1]) {
-      instance._storage[1] = lowerLimit._storage[1];
-    }
-    if (instance._storage[2] < lowerLimit._storage[2]) {
-      instance._storage[2] = lowerLimit._storage[2];
-    }
-    if (instance._storage[3] < lowerLimit._storage[3]) {
-      instance._storage[3] = lowerLimit._storage[3];
-    }
-    return instance;
-  }
-  double get x => _storage[0];
-  double get y => _storage[1];
-  double get z => _storage[2];
-  double get w => _storage[3];
-  Float32x4 get xxxx {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = _storage[0];
-    instance._storage[1] = _storage[0];
-    instance._storage[2] = _storage[0];
-    instance._storage[3] = _storage[0];
-    return instance;
-  }
-  Float32x4 get yyyy {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = _storage[1];
-    instance._storage[1] = _storage[1];
-    instance._storage[2] = _storage[1];
-    instance._storage[3] = _storage[1];
-    return instance;
-  }
-  Float32x4 get zzzz {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = _storage[2];
-    instance._storage[1] = _storage[2];
-    instance._storage[2] = _storage[2];
-    instance._storage[3] = _storage[2];
-    return instance;
-  }
-  Float32x4 get wwww {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = _storage[3];
-    instance._storage[1] = _storage[3];
-    instance._storage[2] = _storage[3];
-    instance._storage[3] = _storage[3];
-    return instance;
-  }
-  Float32x4 withX(double x) {
-    var instance = new _Float32x4Dart.copy(this);
-    instance._storage[0] = x;
-    return instance;
-  }
-  Float32x4 withY(double y) {
-    var instance = new _Float32x4Dart.copy(this);
-    instance._storage[1] = y;
-    return instance;
-  }
-  Float32x4 withZ(double z) {
-    var instance = new _Float32x4Dart.copy(this);
-    instance._storage[2] = z;
-    return instance;
-  }
-  Float32x4 withW(double w) {
-    var instance = new _Float32x4Dart.copy(this);
-    instance._storage[3] = w;
-    return instance;
-  }
-  Float32x4 min(Float32x4 other) {
-    var instance = new _Float32x4Dart.copy(this);
-    if (instance._storage[0] > other._storage[0]) {
-      instance._storage[0] = other._storage[0];
-    }
-    if (instance._storage[1] > other._storage[1]) {
-      instance._storage[1] = other._storage[1];
-    }
-    if (instance._storage[2] > other._storage[2]) {
-      instance._storage[2] = other._storage[2];
-    }
-    if (instance._storage[3] > other._storage[3]) {
-      instance._storage[3] = other._storage[3];
-    }
-    return instance;
-  }
-  Float32x4 max(Float32x4 other) {
-    var instance = new _Float32x4Dart.copy(this);
-    if (instance._storage[0] < other._storage[0]) {
-      instance._storage[0] = other._storage[0];
-    }
-    if (instance._storage[1] < other._storage[1]) {
-      instance._storage[1] = other._storage[1];
-    }
-    if (instance._storage[2] < other._storage[2]) {
-      instance._storage[2] = other._storage[2];
-    }
-    if (instance._storage[3] < other._storage[3]) {
-      instance._storage[3] = other._storage[3];
-    }
-    return instance;
-  }
-  Float32x4 sqrt() {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = _sqrt(_storage[0]);
-    instance._storage[1] = _sqrt(_storage[1]);
-    instance._storage[2] = _sqrt(_storage[2]);
-    instance._storage[3] = _sqrt(_storage[3]);
-    return instance;
-  }
-  Float32x4 reciprocal() {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = (1.0 / _storage[0]);
-    instance._storage[1] = (1.0 / _storage[1]);
-    instance._storage[2] = (1.0 / _storage[2]);
-    instance._storage[3] = (1.0 / _storage[3]);
-    return instance;
-  }
-  Float32x4 reciprocalSqrt() {
-    var instance = new _Float32x4Dart.empty();
-    instance._storage[0] = _sqrt(1.0 / _storage[0]);
-    instance._storage[1] = _sqrt(1.0 / _storage[1]);
-    instance._storage[2] = _sqrt(1.0 / _storage[2]);
-    instance._storage[3] = _sqrt(1.0 / _storage[3]);
-    return instance;
-  }
-  Uint32x4 toUint32x4() {
-    Uint32List view = new Uint32List.view(_storage.asByteArray());
-    return new Uint32x4(view[0], view[1], view[2], view[3]);
-  }
-}
-
-class _Uint32x4Dart implements Uint32x4 {
-  final Uint32List _storage = new Uint32List(4);
-  _Uint32x4Dart.empty() {
-  }
-  _Uint32x4Dart.copy(_Uint32x4Dart other) {
-    _storage[0] = other._storage[0];
-    _storage[1] = other._storage[1];
-    _storage[2] = other._storage[2];
-    _storage[3] = other._storage[3];
-  }
-  factory _Uint32x4Dart(int x, int y, int z, int w) {
-    var instance = new _Uint32x4Dart.empty();
-    instance._storage[0] = x;
-    instance._storage[1] = y;
-    instance._storage[2] = z;
-    instance._storage[3] = w;
-    return instance;
-  }
-  factory _Uint32x4Dart.bool(bool x, bool y, bool z, bool w) {
-    var instance = new _Uint32x4Dart.empty();
-    instance._storage[0] = x ? 0xFFFFFFFF : 0x0;
-    instance._storage[1] = y ? 0xFFFFFFFF : 0x0;
-    instance._storage[2] = z ? 0xFFFFFFFF : 0x0;
-    instance._storage[3] = w ? 0xFFFFFFFF : 0x0;
-    return instance;
-  }
-  Uint32x4 operator |(Uint32x4 other) {
-    var instance = new _Uint32x4Dart.empty();
-    instance._storage[0] = _storage[0] | other._storage[0];
-    instance._storage[1] = _storage[1] | other._storage[1];
-    instance._storage[2] = _storage[2] | other._storage[2];
-    instance._storage[3] = _storage[3] | other._storage[3];
-    return instance;
-  }
-  Uint32x4 operator &(Uint32x4 other) {
-    var instance = new _Uint32x4Dart.empty();
-    instance._storage[0] = _storage[0] & other._storage[0];
-    instance._storage[1] = _storage[1] & other._storage[1];
-    instance._storage[2] = _storage[2] & other._storage[2];
-    instance._storage[3] = _storage[3] & other._storage[3];
-    return instance;
-  }
-  Uint32x4 operator ^(Uint32x4 other) {
-    var instance = new _Uint32x4Dart.empty();
-    instance._storage[0] = _storage[0] ^ other._storage[0];
-    instance._storage[1] = _storage[1] ^ other._storage[1];
-    instance._storage[2] = _storage[2] ^ other._storage[2];
-    instance._storage[3] = _storage[3] ^ other._storage[3];
-    return instance;
-  }
-  int get x => _storage[0];
-  int get y => _storage[1];
-  int get z => _storage[2];
-  int get w => _storage[3];
-  Uint32x4 withX(int x) {
-    var instance = new _Uint32x4Dart.copy(this);
-    instance._storage[0] = x & 0xFFFFFFFF;
-    return instance;
-  }
-  Uint32x4 withY(int y) {
-    var instance = new _Uint32x4Dart.copy(this);
-    instance._storage[1] = y & 0xFFFFFFFF;
-    return instance;
-  }
-  Uint32x4 withZ(int z) {
-    var instance = new _Uint32x4Dart.copy(this);
-    instance._storage[2] = z & 0xFFFFFFFF;
-    return instance;
-  }
-  Uint32x4 withW(int w) {
-    var instance = new _Uint32x4Dart.copy(this);
-    instance._storage[3] = w & 0xFFFFFFFF;
-    return instance;
-  }
-  bool get flagX => _storage[0] != 0x0;
-  bool get flagY => _storage[1] != 0x0;
-  bool get flagZ => _storage[2] != 0x0;
-  bool get flagW => _storage[3] != 0x0;
-  Uint32x4 withFlagX(bool x) {
-    var instance = new _Uint32x4Dart.copy(this);
-    instance._storage[0] = x ? 0xFFFFFFFF : 0x0;
-    return instance;
-  }
-  Uint32x4 withFlagY(bool y) {
-    var instance = new _Uint32x4Dart.copy(this);
-    instance._storage[1] = y ? 0xFFFFFFFF : 0x0;
-    return instance;
-  }
-  Uint32x4 withFlagZ(bool z) {
-    var instance = new _Uint32x4Dart.copy(this);
-    instance._storage[2] = z ? 0xFFFFFFFF : 0x0;
-    return instance;
-  }
-  Uint32x4 withFlagW(bool w) {
-    var instance = new _Uint32x4Dart.copy(this);
-    instance._storage[3] = w ? 0xFFFFFFFF : 0x0;
-    return instance;
-  }
-  Float32x4 select(Float32x4 trueValue,
-                          Float32x4 falseValue) {
-    Uint32x4 trueMask = trueValue.toUint32x4();
-    Uint32x4 falseMask = falseValue.toUint32x4();
-    var instance = new _Uint32x4Dart.empty();
-    instance._storage[0] = (_storage[0] & trueMask._storage[0]);
-    instance._storage[1] = (_storage[1] & trueMask._storage[1]);
-    instance._storage[2] = (_storage[2] & trueMask._storage[2]);
-    instance._storage[3] = (_storage[3] & trueMask._storage[3]);
-    instance._storage[0] |= (~_storage[0] & falseMask._storage[0]);
-    instance._storage[1] |= (~_storage[1] & falseMask._storage[1]);
-    instance._storage[2] |= (~_storage[2] & falseMask._storage[2]);
-    instance._storage[3] |= (~_storage[3] & falseMask._storage[3]);
-    return instance.toFloat32x4();
-  }
-  Float32x4 toFloat32x4() {
-    Float32List view = new Float32List.view(_storage.asByteArray());
-    return new Float32x4(view[0], view[1], view[2], view[3]);
-  }
-}
-
-class _Float32x4 implements Float32x4 {
-  factory _Float32x4(double x, double y, double z, double w)
-      native "Float32x4_fromDoubles";
-  factory _Float32x4.zero() native "Float32x4_zero";
-  Float32x4 operator +(Float32x4 other) {
-    return _add(other);
-  }
-  Float32x4 _add(Float32x4 other) native "Float32x4_add";
-  Float32x4 operator -() {
-    return _negate();
-  }
-  Float32x4 _negate() native "Float32x4_negate";
-  Float32x4 operator -(Float32x4 other) {
-    return _sub(other);
-  }
-  Float32x4 _sub(Float32x4 other) native "Float32x4_sub";
-  Float32x4 operator *(Float32x4 other) {
-    return _mul(other);
-  }
-  Float32x4 _mul(Float32x4 other) native "Float32x4_mul";
-  Float32x4 operator /(Float32x4 other) {
-    return _div(other);
-  }
-  Float32x4 _div(Float32x4 other) native "Float32x4_div";
-  Uint32x4 lessThan(Float32x4 other) {
-    return _cmplt(other);
-  }
-  Uint32x4 _cmplt(Float32x4 other) native "Float32x4_cmplt";
-  Uint32x4 lessThanOrEqual(Float32x4 other) {
-    return _cmplte(other);
-  }
-  Uint32x4 _cmplte(Float32x4 other) native "Float32x4_cmplte";
-  Uint32x4 greaterThan(Float32x4 other) {
-    return _cmpgt(other);
-  }
-  Uint32x4 _cmpgt(Float32x4 other) native "Float32x4_cmpgt";
-  Uint32x4 greaterThanOrEqual(Float32x4 other) {
-    return _cmpgte(other);
-  }
-  Uint32x4 _cmpgte(Float32x4 other) native "Float32x4_cmpgte";
-  Uint32x4 equal(Float32x4 other) {
-    return _cmpequal(other);
-  }
-  Uint32x4 _cmpequal(Float32x4 other)
-      native "Float32x4_cmpequal";
-  Uint32x4 notEqual(Float32x4 other) {
-    return _cmpnequal(other);
-  }
-  Uint32x4 _cmpnequal(Float32x4 other)
-      native "Float32x4_cmpnequal";
-  Float32x4 scale(double s) {
-    return _scale(s);
-  }
-  Float32x4 _scale(double s) native "Float32x4_scale";
-  Float32x4 abs() {
-    return _abs();
-  }
-  Float32x4 _abs() native "Float32x4_abs";
-  Float32x4 clamp(Float32x4 lowerLimit,
-                         Float32x4 upperLimit) {
-    return _clamp(lowerLimit, upperLimit);
-  }
-  Float32x4 _clamp(Float32x4 lowerLimit,
-                          Float32x4 upperLimit)
-      native "Float32x4_clamp";
-  double get x native "Float32x4_getX";
-  double get y native "Float32x4_getY";
-  double get z native "Float32x4_getZ";
-  double get w native "Float32x4_getW";
-  Float32x4 get xxxx native "Float32x4_getXXXX";
-  Float32x4 get yyyy native "Float32x4_getYYYY";
-  Float32x4 get zzzz native "Float32x4_getZZZZ";
-  Float32x4 get wwww native "Float32x4_getWWWW";
-  Float32x4 withX(double x) native "Float32x4_setX";
-  Float32x4 withY(double y) native "Float32x4_setY";
-  Float32x4 withZ(double z) native "Float32x4_setZ";
-  Float32x4 withW(double w) native "Float32x4_setW";
-  Float32x4 min(Float32x4 other) {
-    return _min(other);
-  }
-  Float32x4 _min(Float32x4 other) native "Float32x4_min";
-  Float32x4 max(Float32x4 other) {
-    return _max(other);
-  }
-  Float32x4 _max(Float32x4 other) native "Float32x4_max";
-  Float32x4 sqrt() {
-    return _sqrt();
-  }
-  Float32x4 _sqrt() native "Float32x4_sqrt";
-  Float32x4 reciprocal() {
-    return _reciprocal();
-  }
-  Float32x4 _reciprocal() native "Float32x4_reciprocal";
-  Float32x4 reciprocalSqrt() {
-    return _reciprocalSqrt();
-  }
-  Float32x4 _reciprocalSqrt() native "Float32x4_reciprocalSqrt";
-  Uint32x4 toUint32x4() {
-      return _toUint32x4();
-  }
-  Uint32x4 _toUint32x4() native "Float32x4_toUint32x4";
-}
-
-class _Uint32x4 implements Uint32x4 {
-  factory _Uint32x4(int x, int y, int z, int w)
-      native "Uint32x4_fromInts";
-  factory _Uint32x4.bool(bool x, bool y, bool z, bool w)
-      native "Uint32x4_fromBools";
-  Uint32x4 operator |(Uint32x4 other) {
-    return _or(other);
-  }
-  Uint32x4 _or(Uint32x4 other) native "Uint32x4_or";
-  Uint32x4 operator &(Uint32x4 other) {
-    return _and(other);
-  }
-  Uint32x4 _and(Uint32x4 other) native "Uint32x4_and";
-  Uint32x4 operator ^(Uint32x4 other) {
-    return _xor(other);
-  }
-  Uint32x4 _xor(Uint32x4 other) native "Uint32x4_xor";
-  int get x native "Uint32x4_getX";
-  int get y native "Uint32x4_getY";
-  int get z native "Uint32x4_getZ";
-  int get w native "Uint32x4_getW";
-  Uint32x4 withX(int x) native "Uint32x4_setX";
-  Uint32x4 withY(int y) native "Uint32x4_setY";
-  Uint32x4 withZ(int z) native "Uint32x4_setZ";
-  Uint32x4 withW(int w) native "Uint32x4_setW";
-  bool get flagX native "Uint32x4_getFlagX";
-  bool get flagY native "Uint32x4_getFlagY";
-  bool get flagZ native "Uint32x4_getFlagZ";
-  bool get flagW native "Uint32x4_getFlagW";
-  Uint32x4 withFlagX(bool x) native "Uint32x4_setFlagX";
-  Uint32x4 withFlagY(bool y) native "Uint32x4_setFlagY";
-  Uint32x4 withFlagZ(bool z) native "Uint32x4_setFlagZ";
-  Uint32x4 withFlagW(bool w) native "Uint32x4_setFlagW";
-  Float32x4 select(Float32x4 trueValue,
-                          Float32x4 falseValue) {
-    return _select(trueValue, falseValue);
-  }
-  Float32x4 _select(Float32x4 trueValue,
-                           Float32x4 falseValue)
-      native "Uint32x4_select";
-  Float32x4 toFloat32x4() {
-      return _toFloat32x4();
-  }
-  Float32x4 _toFloat32x4() native "Uint32x4_toFloat32x4";
-}
-
-
-class _Float32x4Array extends _ByteArrayBase
-    implements Float32x4List {
-  factory _Float32x4Array(int length) {
-    return _new(length);
-  }
-
-  factory _Float32x4Array.view(ByteArray array,
-                                    [int start = 0, int length]) {
-    if (length == null) {
-      length = (array.lengthInBytes() - start) ~/ _BYTES_PER_ELEMENT;
-    }
-    return new _Float32x4ArrayView(array, start, length);
-  }
-
-  Float32x4 operator [](int index) {
-    return _getIndexed(index);
-  }
-
-  int operator []=(int index, Float32x4 value) {
-    _setIndexed(index, value);
-  }
-
-  Iterator<Float32x4> get iterator {
-    return new _ByteArrayIterator<Float32x4>(this);
-  }
-
-  List<Float32x4> sublist(int start, [int end]) {
-    if (end == null) end = length;
-    int length = end - start;
-    _rangeCheck(this.length, start, length);
-    List<Float32x4> result = _new(length);
-    result.setRange(0, length, this, start);
-    return result;
-  }
-
-  List<Float32x4> getRange(int start, int length) {
-    return sublist(start, start + length);
-  }
-
-  void setRange(int start, int length, List<Float32x4> from,
-                [int startFrom = 0]) {
-    if (from is _Float32x4Array) {
-      _setRange(start * _BYTES_PER_ELEMENT,
-                length * _BYTES_PER_ELEMENT,
-                from,
-                startFrom * _BYTES_PER_ELEMENT);
-    } else {
-      IterableMixinWorkaround.setRangeList(
-          this, start, length, from, startFrom);
-    }
-  }
-  String toString() {
-    return Collections.collectionToString(this);
-  }
-  int bytesPerElement() {
-    return _BYTES_PER_ELEMENT;
-  }
-  int lengthInBytes() {
-    return _length() * _BYTES_PER_ELEMENT;
-  }
-  static const int _BYTES_PER_ELEMENT = 16;
-  static _Float32x4Array _new(int length)
-      native "Float32x4Array_new";
-  Float32x4 _getIndexed(int index)
-      native "Float32x4Array_getIndexed";
-  int _setIndexed(int index, Float32x4 value)
-      native "Float32x4Array_setIndexed";
-}
-
-
-class _Float32x4ArrayView extends _ByteArrayViewBase
-    implements Float32x4List {
-  _Float32x4ArrayView(ByteArray array,
-                           [int offsetInBytes = 0, int _length])
-    : super(array, _requireInteger(offsetInBytes),
-      _requireIntegerOrNull(
-        _length,
-        ((array.lengthInBytes() - offsetInBytes) ~/ _BYTES_PER_ELEMENT))) {
-    _rangeCheck(array.lengthInBytes(), _offset, length * _BYTES_PER_ELEMENT);
-  }
-
-  Float32x4 operator [](int index) {
-    if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
-    }
-    return _array.getFloat32x4(_offset + (index * _BYTES_PER_ELEMENT));
-  }
-
-  void operator []=(int index, Float32x4 value) {
-    if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
-    }
-    _array.setFloat32x4(_offset + (index * _BYTES_PER_ELEMENT), value);
-  }
-
-  Iterator<Float32x4> get iterator {
-    return new _ByteArrayIterator<Float32x4>(this);
-  }
-
-  List<Float32x4> sublist(int start, [int end]) {
-    if (end == null) end = length;
-    int length = end - start;
-    _rangeCheck(this.length, start, length);
-    List<Float32x4> result = new Float32List(length);
-    result.setRange(0, length, this, start);
-    return result;
-  }
-
-  List<Float32x4> getRange(int start, int length) {
-    return sublist(start, start + length);
-  }
-
-  void setRange(int start, int length, List<Float32x4> from,
-               [int startFrom = 0]) {
-    IterableMixinWorkaround.setRangeList(this, start, length, from, startFrom);
-  }
-
-  String toString() {
-    return Collections.collectionToString(this);
-  }
-
-  int bytesPerElement() {
-    return _BYTES_PER_ELEMENT;
-  }
-
-  int lengthInBytes() {
-    return length * _BYTES_PER_ELEMENT;
-  }
-
-  ByteArray asByteArray([int start = 0, int length]) {
-    if (length == null) {
-      length = this.lengthInBytes();
-    }
-    _rangeCheck(this.length, start, length);
-    return _array.subByteArray(_offset + start, length);
-  }
-
-  static const int _BYTES_PER_ELEMENT = 16;
-}
-
-
-class _ExternalFloat32x4Array extends _ByteArrayBase
-  implements Float32x4List {
-  Float32x4 operator [](int index) {
-    return _getIndexed(index);
-  }
-
-  int operator []=(int index, Float32x4 value) {
-    _setIndexed(index, value);
-  }
-
-  Iterator<Float32x4> get iterator {
-    return new _ByteArrayIterator<Float32x4>(this);
-  }
-
-  List<Float32x4> sublist(int start, [int end]) {
-    if (end == null) end = length;
-    int length = end - start;
-    _rangeCheck(this.length, start, length);
-    List<Float32x4> result = new Float32x4List(length);
-    result.setRange(0, length, this, start);
-    return result;
-  }
-
-  List<Float32x4> getRange(int start, int length) {
-    return sublist(start, start + length);
-  }
-
-  void setRange(int start, int length, List<Float32x4> from,
-                [int startFrom = 0]) {
-    if (from is _ExternalFloat32x4Array) {
-      _setRange(start * _BYTES_PER_ELEMENT,
-                length * _BYTES_PER_ELEMENT,
-                from,
-                startFrom * _BYTES_PER_ELEMENT);
-    } else {
-      IterableMixinWorkaround.setRangeList(
-          this, start, length, from, startFrom);
-    }
-  }
-
-  String toString() {
-    return Collections.collectionToString(this);
-  }
-
-  int bytesPerElement() {
-    return _BYTES_PER_ELEMENT;
-  }
-
-  int lengthInBytes() {
-    return _length() * _BYTES_PER_ELEMENT;
-  }
-
-  static const int _BYTES_PER_ELEMENT = 16;
-
-  Float32x4 _getIndexed(int index)
-      native "ExternalFloat32x4Array_getIndexed";
-  int _setIndexed(int index, Float32x4 value)
-      native "ExternalFloat32x4Array_setIndexed";
-}
diff --git a/runtime/lib/string_base.dart b/runtime/lib/string_base.dart
deleted file mode 100644
index b2d126b..0000000
--- a/runtime/lib/string_base.dart
+++ /dev/null
@@ -1,608 +0,0 @@
-// Copyright (c) 2012, 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.
-
-/**
- * [_StringBase] contains common methods used by concrete String
- * implementations, e.g., _OneByteString.
- */
-class _StringBase {
-
-  factory _StringBase._uninstantiable() {
-    throw new UnsupportedError(
-        "_StringBase can't be instaniated");
-  }
-
-  int get hashCode native "String_getHashCode";
-
-  /**
-   *  Create the most efficient string representation for specified
-   *  [codePoints].
-   */
-  static String createFromCharCodes(Iterable<int> charCodes) {
-    if (charCodes is! _ObjectArray && charCodes is! _GrowableObjectArray) {
-      charCodes = new List<int>.from(charCodes, growable: false);
-    }
-    return _createFromCodePoints(charCodes);
-  }
-
-  static String _createFromCodePoints(List<int> codePoints)
-      native "StringBase_createFromCodePoints";
-
-  String operator [](int index) native "String_charAt";
-
-  int codeUnitAt(int index) native "String_codeUnitAt";
-
-  int get length native "String_getLength";
-
-  bool get isEmpty {
-    return this.length == 0;
-  }
-
-  String operator +(String other) native "String_concat";
-
-  String concat(String other) => this + other;
-
-  String toString() {
-    return this;
-  }
-
-  bool operator ==(Object other) {
-    if (identical(this, other)) {
-      return true;
-    }
-    if ((other is !String) ||
-        (this.length != other.length)) {
-      // TODO(5413632): Compare hash codes when both are present.
-      return false;
-    }
-    return this.compareTo(other) == 0;
-  }
-
-  int compareTo(String other) {
-    int thisLength = this.length;
-    int otherLength = other.length;
-    int len = (thisLength < otherLength) ? thisLength : otherLength;
-    for (int i = 0; i < len; i++) {
-      int thisCodePoint = this.codeUnitAt(i);
-      int otherCodePoint = other.codeUnitAt(i);
-      if (thisCodePoint < otherCodePoint) {
-        return -1;
-      }
-      if (thisCodePoint > otherCodePoint) {
-        return 1;
-      }
-    }
-    if (thisLength < otherLength) return -1;
-    if (thisLength > otherLength) return 1;
-    return 0;
-  }
-
-  bool _substringMatches(int start, String other) {
-    if (other.isEmpty) return true;
-    if ((start < 0) || (start >= this.length)) {
-      return false;
-    }
-    final int len = other.length;
-    if ((start + len) > this.length) {
-      return false;
-    }
-    for (int i = 0; i < len; i++) {
-      if (this.codeUnitAt(i + start) != other.codeUnitAt(i)) {
-        return false;
-      }
-    }
-    return true;
-  }
-
-  bool endsWith(String other) {
-    return _substringMatches(this.length - other.length, other);
-  }
-
-  bool startsWith(String other) {
-    return _substringMatches(0, other);
-  }
-
-  int indexOf(String other, [int start = 0]) {
-    if (other.isEmpty) {
-      return start < this.length ? start : this.length;
-    }
-    if ((start < 0) || (start >= this.length)) {
-      return -1;
-    }
-    int len = this.length - other.length + 1;
-    for (int index = start; index < len; index++) {
-      if (_substringMatches(index, other)) {
-        return index;
-      }
-    }
-    return -1;
-  }
-
-  int lastIndexOf(String other, [int start = null]) {
-    if (start == null) start = length - 1;
-    if (other.isEmpty) {
-      return min(this.length, start);
-    }
-    if (start >= this.length) {
-      start = this.length - 1;
-    }
-    for (int index = start; index >= 0; index--) {
-      if (_substringMatches(index, other)) {
-        return index;
-      }
-    }
-    return -1;
-  }
-
-  String substring(int startIndex, [int endIndex]) {
-    if (endIndex == null) endIndex = this.length;
-
-    if ((startIndex < 0) || (startIndex > this.length)) {
-      throw new RangeError.value(startIndex);
-    }
-    if ((endIndex < 0) || (endIndex > this.length)) {
-      throw new RangeError.value(endIndex);
-    }
-    if (startIndex > endIndex) {
-      throw new RangeError.value(startIndex);
-    }
-    return _substringUnchecked(startIndex, endIndex);
-  }
-
-  String slice([int startIndex, int endIndex]) {
-    int start, end;
-    if (startIndex == null) {
-      start = 0;
-    } else if (startIndex is! int) {
-      throw new ArgumentError("startIndex is not int");
-    } else if (startIndex >= 0) {
-      start = startIndex;
-    } else {
-      start = this.length + startIndex;
-    }
-    if (start < 0 || start > this.length) {
-      throw new RangeError(
-          "startIndex out of range: $startIndex (length: $length)");
-    }
-    if (endIndex == null) {
-      end = this.length;
-    } else if (endIndex is! int) {
-      throw new ArgumentError("endIndex is not int");
-    } else if (endIndex >= 0) {
-      end = endIndex;
-    } else {
-      end = this.length + endIndex;
-    }
-    if (end < 0 || end > this.length) {
-      throw new RangeError(
-          "endIndex out of range: $endIndex (length: $length)");
-    }
-    if (end < start) {
-      throw new ArgumentError(
-          "End before start: $endIndex < $startIndex (length: $length)");
-    }
-    return _substringUnchecked(start, end);
-  }
-
-  String _substringUnchecked(int startIndex, int endIndex) {
-    assert(endIndex != null);
-    assert((startIndex >= 0) && (startIndex <= this.length));
-    assert((endIndex >= 0) && (endIndex <= this.length));
-    assert(startIndex <= endIndex);
-
-    if (startIndex == endIndex) {
-      return "";
-    }
-    if ((startIndex + 1) == endIndex) {
-      return this[startIndex];
-    }
-    return _substringUncheckedNative(startIndex, endIndex);
-  }
-
-  String _substringUncheckedNative(int startIndex, int endIndex)
-      native "StringBase_substringUnchecked";
-
-  String trim() {
-    final int len = this.length;
-    int first = 0;
-    for (; first < len; first++) {
-      if (!_isWhitespace(this.codeUnitAt(first))) {
-        break;
-      }
-    }
-    if (len == first) {
-      // String contains only whitespaces.
-      return "";
-    }
-    int last = len - 1;
-    for (; last >= first; last--) {
-      if (!_isWhitespace(this.codeUnitAt(last))) {
-        break;
-      }
-    }
-    if ((first == 0) && (last == (len - 1))) {
-      // Returns this string if it does not have leading or trailing
-      // whitespaces.
-      return this;
-    } else {
-      return _substringUnchecked(first, last + 1);
-    }
-  }
-
-  bool contains(Pattern pattern, [int startIndex = 0]) {
-    if (pattern is String) {
-      return indexOf(pattern, startIndex) >= 0;
-    }
-    return pattern.allMatches(this.substring(startIndex)).iterator.moveNext();
-  }
-
-  String replaceFirst(Pattern pattern, String replacement) {
-    if (pattern is! Pattern) {
-      throw new ArgumentError("${pattern} is not a Pattern");
-    }
-    if (replacement is! String) {
-      throw new ArgumentError("${replacement} is not a String");
-    }
-    StringBuffer buffer = new StringBuffer();
-    int startIndex = 0;
-    Iterator iterator = pattern.allMatches(this).iterator;
-    if (iterator.moveNext()) {
-      Match match = iterator.current;
-      buffer..write(this.substring(startIndex, match.start))
-            ..write(replacement);
-      startIndex = match.end;
-    }
-    return (buffer..write(this.substring(startIndex))).toString();
-  }
-
-  String replaceAll(Pattern pattern, String replacement) {
-    if (pattern is! Pattern) {
-      throw new ArgumentError("${pattern} is not a Pattern");
-    }
-    if (replacement is! String) {
-      throw new ArgumentError(
-          "${replacement} is not a String or Match->String function");
-    }
-    StringBuffer buffer = new StringBuffer();
-    int startIndex = 0;
-    for (Match match in pattern.allMatches(this)) {
-      buffer..write(this.substring(startIndex, match.start))
-            ..write(replacement);
-      startIndex = match.end;
-    }
-    return (buffer..write(this.substring(startIndex))).toString();
-  }
-
-  String replaceAllMapped(Pattern pattern, String replace(Match match)) {
-    return splitMapJoin(pattern, onMatch: replace);
-  }
-
-  static String _matchString(Match match) => match[0];
-  static String _stringIdentity(String string) => string;
-
-  String _splitMapJoinEmptyString(String onMatch(Match match),
-                                  String onNonMatch(String nonMatch)) {
-    // Pattern is the empty string.
-    StringBuffer buffer = new StringBuffer();
-    int length = this.length;
-    int i = 0;
-    buffer.write(onNonMatch(""));
-    while (i < length) {
-      buffer.write(onMatch(new _StringMatch(i, this, "")));
-      // Special case to avoid splitting a surrogate pair.
-      int code = this.codeUnitAt(i);
-      if ((code & ~0x3FF) == 0xD800 && length > i + 1) {
-        // Leading surrogate;
-        code = this.codeUnitAt(i + 1);
-        if ((code & ~0x3FF) == 0xDC00) {
-          // Matching trailing surrogate.
-          buffer.write(onNonMatch(this.substring(i, i + 2)));
-          i += 2;
-          continue;
-        }
-      }
-      buffer.write(onNonMatch(this[i]));
-      i++;
-    }
-    buffer.write(onMatch(new _StringMatch(i, this, "")));
-    buffer.write(onNonMatch(""));
-    return buffer.toString();
-  }
-
-  String splitMapJoin(Pattern pattern,
-                      {String onMatch(Match match),
-                       String onNonMatch(String nonMatch)}) {
-    if (pattern is! Pattern) {
-      throw new ArgumentError("${pattern} is not a Pattern");
-    }
-    if (onMatch == null) onMatch = _matchString;
-    if (onNonMatch == null) onNonMatch = _stringIdentity;
-    if (pattern is String) {
-      String stringPattern = pattern;
-      if (stringPattern.isEmpty) {
-        return _splitMapJoinEmptyString(onMatch, onNonMatch);
-      }
-    }
-    StringBuffer buffer = new StringBuffer();
-    int startIndex = 0;
-    for (Match match in pattern.allMatches(this)) {
-      buffer.write(onNonMatch(this.substring(startIndex, match.start)));
-      buffer.write(onMatch(match).toString());
-      startIndex = match.end;
-    }
-    buffer.write(onNonMatch(this.substring(startIndex)));
-    return buffer.toString();
-  }
-
-
-  /**
-   * Convert all objects in [values] to strings and concat them
-   * into a result string.
-   */
-  static String _interpolate(List values) {
-    int numValues = values.length;
-    var stringList = new List(numValues);
-    for (int i = 0; i < numValues; i++) {
-      stringList[i] = values[i].toString();
-    }
-    return _concatAll(stringList);
-  }
-
-  Iterable<Match> allMatches(String str) {
-    List<Match> result = new List<Match>();
-    int length = str.length;
-    int patternLength = this.length;
-    int startIndex = 0;
-    while (true) {
-      int position = str.indexOf(this, startIndex);
-      if (position == -1) {
-        break;
-      }
-      result.add(new _StringMatch(position, str, this));
-      int endIndex = position + patternLength;
-      if (endIndex == length) {
-        break;
-      } else if (position == endIndex) {
-        ++startIndex;  // empty match, advance and restart
-      } else {
-        startIndex = endIndex;
-      }
-    }
-    return result;
-  }
-
-  List<String> split(Pattern pattern) {
-    if ((pattern is String) && pattern.isEmpty) {
-      List<String> result = new List<String>(length);
-      for (int i = 0; i < length; i++) {
-        result[i] = this[i];
-      }
-      return result;
-    }
-    int length = this.length;
-    Iterator iterator = pattern.allMatches(this).iterator;
-    if (length == 0 && iterator.moveNext()) {
-      // A matched empty string input returns the empty list.
-      return <String>[];
-    }
-    List<String> result = new List<String>();
-    int startIndex = 0;
-    int previousIndex = 0;
-    while (true) {
-      if (startIndex == length || !iterator.moveNext()) {
-        result.add(this._substringUnchecked(previousIndex, length));
-        break;
-      }
-      Match match = iterator.current;
-      if (match.start == length) {
-        result.add(this._substringUnchecked(previousIndex, length));
-        break;
-      }
-      int endIndex = match.end;
-      if (startIndex == endIndex && endIndex == previousIndex) {
-        ++startIndex;  // empty match, advance and restart
-        continue;
-      }
-      result.add(this._substringUnchecked(previousIndex, match.start));
-      startIndex = previousIndex = endIndex;
-    }
-    return result;
-  }
-
-  List<int> get codeUnits => new CodeUnits(this);
-
-  Runes get runes => new Runes(this);
-
-  String toUpperCase() native "String_toUpperCase";
-
-  String toLowerCase() native "String_toLowerCase";
-
-  // Implementations of Strings methods follow below.
-  static String join(Iterable<String> strings, String separator) {
-    bool first = true;
-    List<String> stringsList = <String>[];
-    for (String string in strings) {
-      if (first) {
-        first = false;
-      } else {
-        stringsList.add(separator);
-      }
-
-      if (string is! String) {
-        throw new ArgumentError(Error.safeToString(string));
-      }
-      stringsList.add(string);
-    }
-    return concatAll(stringsList);
-  }
-
-  static String concatAll(Iterable<String> strings) {
-    _ObjectArray stringsArray;
-    if (strings is _ObjectArray) {
-      stringsArray = strings;
-      for (int i = 0; i < strings.length; i++) {
-        if (strings[i] is! String) throw new ArgumentError(strings[i]);
-      }
-    } else {
-      int len = strings.length;
-      stringsArray = new _ObjectArray(len);
-      int i = 0;
-      for (String string in strings) {
-        if (string is! String) throw new ArgumentError(string);
-        stringsArray[i++] = string;
-      }
-    }
-    return _concatAll(stringsArray);
-  }
-
-  static String _concatAll(List<String> strings)
-      native "Strings_concatAll";
-}
-
-
-class _OneByteString extends _StringBase implements String {
-  factory _OneByteString._uninstantiable() {
-    throw new UnsupportedError(
-        "_OneByteString can only be allocated by the VM");
-  }
-
-  int get hashCode native "String_getHashCode";
-
-  // Checks for one-byte whitespaces only.
-  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
-  // whitespaces for one byte strings.
-  bool _isWhitespace(int codePoint) {
-    return
-      (codePoint == 32) || // Space.
-      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
-  }
-
-  String _substringUncheckedNative(int startIndex, int endIndex)
-      native "OneByteString_substringUnchecked";
-
-  List<String> _splitWithCharCode(int charCode)
-      native "OneByteString_splitWithCharCode";
-
-  List<String> split(Pattern pattern) {
-    if ((pattern is _OneByteString) && (pattern.length == 1)) {
-      return _splitWithCharCode(pattern.codeUnitAt(0));
-    }
-    return super.split(pattern);
-  }
-}
-
-
-class _TwoByteString extends _StringBase implements String {
-  factory _TwoByteString._uninstantiable() {
-    throw new UnsupportedError(
-        "_TwoByteString can only be allocated by the VM");
-  }
-
-  // Checks for one-byte whitespaces only.
-  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
-  // whitespaces. Add checking for multi-byte whitespace codepoints.
-  bool _isWhitespace(int codePoint) {
-    return
-      (codePoint == 32) || // Space.
-      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
-  }
-}
-
-
-class _FourByteString extends _StringBase implements String {
-  factory _FourByteString._uninstantiable() {
-    throw new UnsupportedError(
-        "_FourByteString can only be allocated by the VM");
-  }
-
-  // Checks for one-byte whitespaces only.
-  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
-  // whitespaces. Add checking for multi-byte whitespace codepoints.
-  bool _isWhitespace(int codePoint) {
-    return
-      (codePoint == 32) || // Space.
-      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
-  }
-}
-
-
-class _ExternalOneByteString extends _StringBase implements String {
-  factory _ExternalOneByteString._uninstantiable() {
-    throw new UnsupportedError(
-        "_ExternalOneByteString can only be allocated by the VM");
-  }
-
-  // Checks for one-byte whitespaces only.
-  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
-  // whitespaces for one byte strings.
-  bool _isWhitespace(int codePoint) {
-    return
-      (codePoint == 32) || // Space.
-      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
-  }
-}
-
-
-class _ExternalTwoByteString extends _StringBase implements String {
-  factory _ExternalTwoByteString._uninstantiable() {
-    throw new UnsupportedError(
-        "_ExternalTwoByteString can only be allocated by the VM");
-  }
-
-  // Checks for one-byte whitespaces only.
-  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
-  // whitespaces. Add checking for multi-byte whitespace codepoints.
-  bool _isWhitespace(int codePoint) {
-    return
-      (codePoint == 32) || // Space.
-      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
-  }
-}
-
-
-class _ExternalFourByteString extends _StringBase implements String {
-  factory _ExternalFourByteString._uninstantiable() {
-    throw new UnsupportedError(
-        "ExternalFourByteString can only be allocated by the VM");
-  }
-
-  // Checks for one-byte whitespaces only.
-  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
-  // whitespaces. Add checking for multi-byte whitespace codepoints.
-  bool _isWhitespace(int codePoint) {
-    return
-      (codePoint == 32) || // Space.
-      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
-  }
-}
-
-
-class _StringMatch implements Match {
-  const _StringMatch(int this.start,
-                     String this.str,
-                     String this.pattern);
-
-  int get end => start + pattern.length;
-  String operator[](int g) => group(g);
-  int get groupCount => 0;
-
-  String group(int group) {
-    if (group != 0) {
-      throw new RangeError.value(group);
-    }
-    return pattern;
-  }
-
-  List<String> groups(List<int> groups) {
-    List<String> result = new List<String>();
-    for (int g in groups) {
-      result.add(group(g));
-    }
-    return result;
-  }
-
-  final int start;
-  final String str;
-  final String pattern;
-}
diff --git a/runtime/lib/string_patch.dart b/runtime/lib/string_patch.dart
index 48035d4..1ba5e1a 100644
--- a/runtime/lib/string_patch.dart
+++ b/runtime/lib/string_patch.dart
@@ -7,3 +7,609 @@
     return _StringBase.createFromCharCodes(charCodes);
   }
 }
+
+
+/**
+ * [_StringBase] contains common methods used by concrete String
+ * implementations, e.g., _OneByteString.
+ */
+class _StringBase {
+
+  factory _StringBase._uninstantiable() {
+    throw new UnsupportedError(
+        "_StringBase can't be instaniated");
+  }
+
+  int get hashCode native "String_getHashCode";
+
+  /**
+   *  Create the most efficient string representation for specified
+   *  [codePoints].
+   */
+  static String createFromCharCodes(Iterable<int> charCodes) {
+    if (charCodes is! _ObjectArray && charCodes is! _GrowableObjectArray) {
+      charCodes = new List<int>.from(charCodes, growable: false);
+    }
+    return _createFromCodePoints(charCodes);
+  }
+
+  static String _createFromCodePoints(List<int> codePoints)
+      native "StringBase_createFromCodePoints";
+
+  String operator [](int index) native "String_charAt";
+
+  int codeUnitAt(int index) native "String_codeUnitAt";
+
+  int get length native "String_getLength";
+
+  bool get isEmpty {
+    return this.length == 0;
+  }
+
+  String operator +(String other) native "String_concat";
+
+  String concat(String other) => this + other;
+
+  String toString() {
+    return this;
+  }
+
+  bool operator ==(Object other) {
+    if (identical(this, other)) {
+      return true;
+    }
+    if ((other is !String) ||
+        (this.length != other.length)) {
+      // TODO(5413632): Compare hash codes when both are present.
+      return false;
+    }
+    return this.compareTo(other) == 0;
+  }
+
+  int compareTo(String other) {
+    int thisLength = this.length;
+    int otherLength = other.length;
+    int len = (thisLength < otherLength) ? thisLength : otherLength;
+    for (int i = 0; i < len; i++) {
+      int thisCodePoint = this.codeUnitAt(i);
+      int otherCodePoint = other.codeUnitAt(i);
+      if (thisCodePoint < otherCodePoint) {
+        return -1;
+      }
+      if (thisCodePoint > otherCodePoint) {
+        return 1;
+      }
+    }
+    if (thisLength < otherLength) return -1;
+    if (thisLength > otherLength) return 1;
+    return 0;
+  }
+
+  bool _substringMatches(int start, String other) {
+    if (other.isEmpty) return true;
+    if ((start < 0) || (start >= this.length)) {
+      return false;
+    }
+    final int len = other.length;
+    if ((start + len) > this.length) {
+      return false;
+    }
+    for (int i = 0; i < len; i++) {
+      if (this.codeUnitAt(i + start) != other.codeUnitAt(i)) {
+        return false;
+      }
+    }
+    return true;
+  }
+
+  bool endsWith(String other) {
+    return _substringMatches(this.length - other.length, other);
+  }
+
+  bool startsWith(String other) {
+    return _substringMatches(0, other);
+  }
+
+  int indexOf(String other, [int start = 0]) {
+    if (other.isEmpty) {
+      return start < this.length ? start : this.length;
+    }
+    if ((start < 0) || (start >= this.length)) {
+      return -1;
+    }
+    int len = this.length - other.length + 1;
+    for (int index = start; index < len; index++) {
+      if (_substringMatches(index, other)) {
+        return index;
+      }
+    }
+    return -1;
+  }
+
+  int lastIndexOf(String other, [int start = null]) {
+    if (start == null) start = length - 1;
+    if (other.isEmpty) {
+      return min(this.length, start);
+    }
+    if (start >= this.length) {
+      start = this.length - 1;
+    }
+    for (int index = start; index >= 0; index--) {
+      if (_substringMatches(index, other)) {
+        return index;
+      }
+    }
+    return -1;
+  }
+
+  String substring(int startIndex, [int endIndex]) {
+    if (endIndex == null) endIndex = this.length;
+
+    if ((startIndex < 0) || (startIndex > this.length)) {
+      throw new RangeError.value(startIndex);
+    }
+    if ((endIndex < 0) || (endIndex > this.length)) {
+      throw new RangeError.value(endIndex);
+    }
+    if (startIndex > endIndex) {
+      throw new RangeError.value(startIndex);
+    }
+    return _substringUnchecked(startIndex, endIndex);
+  }
+
+  String slice([int startIndex, int endIndex]) {
+    int start, end;
+    if (startIndex == null) {
+      start = 0;
+    } else if (startIndex is! int) {
+      throw new ArgumentError("startIndex is not int");
+    } else if (startIndex >= 0) {
+      start = startIndex;
+    } else {
+      start = this.length + startIndex;
+    }
+    if (start < 0 || start > this.length) {
+      throw new RangeError(
+          "startIndex out of range: $startIndex (length: $length)");
+    }
+    if (endIndex == null) {
+      end = this.length;
+    } else if (endIndex is! int) {
+      throw new ArgumentError("endIndex is not int");
+    } else if (endIndex >= 0) {
+      end = endIndex;
+    } else {
+      end = this.length + endIndex;
+    }
+    if (end < 0 || end > this.length) {
+      throw new RangeError(
+          "endIndex out of range: $endIndex (length: $length)");
+    }
+    if (end < start) {
+      throw new ArgumentError(
+          "End before start: $endIndex < $startIndex (length: $length)");
+    }
+    return _substringUnchecked(start, end);
+  }
+
+  String _substringUnchecked(int startIndex, int endIndex) {
+    assert(endIndex != null);
+    assert((startIndex >= 0) && (startIndex <= this.length));
+    assert((endIndex >= 0) && (endIndex <= this.length));
+    assert(startIndex <= endIndex);
+
+    if (startIndex == endIndex) {
+      return "";
+    }
+    if ((startIndex + 1) == endIndex) {
+      return this[startIndex];
+    }
+    return _substringUncheckedNative(startIndex, endIndex);
+  }
+
+  String _substringUncheckedNative(int startIndex, int endIndex)
+      native "StringBase_substringUnchecked";
+
+  String trim() {
+    final int len = this.length;
+    int first = 0;
+    for (; first < len; first++) {
+      if (!_isWhitespace(this.codeUnitAt(first))) {
+        break;
+      }
+    }
+    if (len == first) {
+      // String contains only whitespaces.
+      return "";
+    }
+    int last = len - 1;
+    for (; last >= first; last--) {
+      if (!_isWhitespace(this.codeUnitAt(last))) {
+        break;
+      }
+    }
+    if ((first == 0) && (last == (len - 1))) {
+      // Returns this string if it does not have leading or trailing
+      // whitespaces.
+      return this;
+    } else {
+      return _substringUnchecked(first, last + 1);
+    }
+  }
+
+  bool contains(Pattern pattern, [int startIndex = 0]) {
+    if (pattern is String) {
+      return indexOf(pattern, startIndex) >= 0;
+    }
+    return pattern.allMatches(this.substring(startIndex)).iterator.moveNext();
+  }
+
+  String replaceFirst(Pattern pattern, String replacement) {
+    if (pattern is! Pattern) {
+      throw new ArgumentError("${pattern} is not a Pattern");
+    }
+    if (replacement is! String) {
+      throw new ArgumentError("${replacement} is not a String");
+    }
+    StringBuffer buffer = new StringBuffer();
+    int startIndex = 0;
+    Iterator iterator = pattern.allMatches(this).iterator;
+    if (iterator.moveNext()) {
+      Match match = iterator.current;
+      buffer..write(this.substring(startIndex, match.start))
+            ..write(replacement);
+      startIndex = match.end;
+    }
+    return (buffer..write(this.substring(startIndex))).toString();
+  }
+
+  String replaceAll(Pattern pattern, String replacement) {
+    if (pattern is! Pattern) {
+      throw new ArgumentError("${pattern} is not a Pattern");
+    }
+    if (replacement is! String) {
+      throw new ArgumentError(
+          "${replacement} is not a String or Match->String function");
+    }
+    StringBuffer buffer = new StringBuffer();
+    int startIndex = 0;
+    for (Match match in pattern.allMatches(this)) {
+      buffer..write(this.substring(startIndex, match.start))
+            ..write(replacement);
+      startIndex = match.end;
+    }
+    return (buffer..write(this.substring(startIndex))).toString();
+  }
+
+  String replaceAllMapped(Pattern pattern, String replace(Match match)) {
+    return splitMapJoin(pattern, onMatch: replace);
+  }
+
+  static String _matchString(Match match) => match[0];
+  static String _stringIdentity(String string) => string;
+
+  String _splitMapJoinEmptyString(String onMatch(Match match),
+                                  String onNonMatch(String nonMatch)) {
+    // Pattern is the empty string.
+    StringBuffer buffer = new StringBuffer();
+    int length = this.length;
+    int i = 0;
+    buffer.write(onNonMatch(""));
+    while (i < length) {
+      buffer.write(onMatch(new _StringMatch(i, this, "")));
+      // Special case to avoid splitting a surrogate pair.
+      int code = this.codeUnitAt(i);
+      if ((code & ~0x3FF) == 0xD800 && length > i + 1) {
+        // Leading surrogate;
+        code = this.codeUnitAt(i + 1);
+        if ((code & ~0x3FF) == 0xDC00) {
+          // Matching trailing surrogate.
+          buffer.write(onNonMatch(this.substring(i, i + 2)));
+          i += 2;
+          continue;
+        }
+      }
+      buffer.write(onNonMatch(this[i]));
+      i++;
+    }
+    buffer.write(onMatch(new _StringMatch(i, this, "")));
+    buffer.write(onNonMatch(""));
+    return buffer.toString();
+  }
+
+  String splitMapJoin(Pattern pattern,
+                      {String onMatch(Match match),
+                       String onNonMatch(String nonMatch)}) {
+    if (pattern is! Pattern) {
+      throw new ArgumentError("${pattern} is not a Pattern");
+    }
+    if (onMatch == null) onMatch = _matchString;
+    if (onNonMatch == null) onNonMatch = _stringIdentity;
+    if (pattern is String) {
+      String stringPattern = pattern;
+      if (stringPattern.isEmpty) {
+        return _splitMapJoinEmptyString(onMatch, onNonMatch);
+      }
+    }
+    StringBuffer buffer = new StringBuffer();
+    int startIndex = 0;
+    for (Match match in pattern.allMatches(this)) {
+      buffer.write(onNonMatch(this.substring(startIndex, match.start)));
+      buffer.write(onMatch(match).toString());
+      startIndex = match.end;
+    }
+    buffer.write(onNonMatch(this.substring(startIndex)));
+    return buffer.toString();
+  }
+
+
+  /**
+   * Convert all objects in [values] to strings and concat them
+   * into a result string.
+   */
+  static String _interpolate(List values) {
+    int numValues = values.length;
+    var stringList = new List(numValues);
+    for (int i = 0; i < numValues; i++) {
+      stringList[i] = values[i].toString();
+    }
+    return _concatAll(stringList);
+  }
+
+  Iterable<Match> allMatches(String str) {
+    List<Match> result = new List<Match>();
+    int length = str.length;
+    int patternLength = this.length;
+    int startIndex = 0;
+    while (true) {
+      int position = str.indexOf(this, startIndex);
+      if (position == -1) {
+        break;
+      }
+      result.add(new _StringMatch(position, str, this));
+      int endIndex = position + patternLength;
+      if (endIndex == length) {
+        break;
+      } else if (position == endIndex) {
+        ++startIndex;  // empty match, advance and restart
+      } else {
+        startIndex = endIndex;
+      }
+    }
+    return result;
+  }
+
+  List<String> split(Pattern pattern) {
+    if ((pattern is String) && pattern.isEmpty) {
+      List<String> result = new List<String>(length);
+      for (int i = 0; i < length; i++) {
+        result[i] = this[i];
+      }
+      return result;
+    }
+    int length = this.length;
+    Iterator iterator = pattern.allMatches(this).iterator;
+    if (length == 0 && iterator.moveNext()) {
+      // A matched empty string input returns the empty list.
+      return <String>[];
+    }
+    List<String> result = new List<String>();
+    int startIndex = 0;
+    int previousIndex = 0;
+    while (true) {
+      if (startIndex == length || !iterator.moveNext()) {
+        result.add(this._substringUnchecked(previousIndex, length));
+        break;
+      }
+      Match match = iterator.current;
+      if (match.start == length) {
+        result.add(this._substringUnchecked(previousIndex, length));
+        break;
+      }
+      int endIndex = match.end;
+      if (startIndex == endIndex && endIndex == previousIndex) {
+        ++startIndex;  // empty match, advance and restart
+        continue;
+      }
+      result.add(this._substringUnchecked(previousIndex, match.start));
+      startIndex = previousIndex = endIndex;
+    }
+    return result;
+  }
+
+  List<int> get codeUnits => new CodeUnits(this);
+
+  Runes get runes => new Runes(this);
+
+  String toUpperCase() native "String_toUpperCase";
+
+  String toLowerCase() native "String_toLowerCase";
+
+  // Implementations of Strings methods follow below.
+  static String join(Iterable<String> strings, String separator) {
+    bool first = true;
+    List<String> stringsList = <String>[];
+    for (String string in strings) {
+      if (first) {
+        first = false;
+      } else {
+        stringsList.add(separator);
+      }
+
+      if (string is! String) {
+        throw new ArgumentError(Error.safeToString(string));
+      }
+      stringsList.add(string);
+    }
+    return concatAll(stringsList);
+  }
+
+  static String concatAll(Iterable<String> strings) {
+    _ObjectArray stringsArray;
+    if (strings is _ObjectArray) {
+      stringsArray = strings;
+      for (int i = 0; i < strings.length; i++) {
+        if (strings[i] is! String) throw new ArgumentError(strings[i]);
+      }
+    } else {
+      int len = strings.length;
+      stringsArray = new _ObjectArray(len);
+      int i = 0;
+      for (String string in strings) {
+        if (string is! String) throw new ArgumentError(string);
+        stringsArray[i++] = string;
+      }
+    }
+    return _concatAll(stringsArray);
+  }
+
+  static String _concatAll(List<String> strings)
+      native "Strings_concatAll";
+}
+
+
+class _OneByteString extends _StringBase implements String {
+  factory _OneByteString._uninstantiable() {
+    throw new UnsupportedError(
+        "_OneByteString can only be allocated by the VM");
+  }
+
+  int get hashCode native "String_getHashCode";
+
+  // Checks for one-byte whitespaces only.
+  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
+  // whitespaces for one byte strings.
+  bool _isWhitespace(int codePoint) {
+    return
+      (codePoint == 32) || // Space.
+      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
+  }
+
+  String _substringUncheckedNative(int startIndex, int endIndex)
+      native "OneByteString_substringUnchecked";
+
+  List<String> _splitWithCharCode(int charCode)
+      native "OneByteString_splitWithCharCode";
+
+  List<String> split(Pattern pattern) {
+    if ((pattern is _OneByteString) && (pattern.length == 1)) {
+      return _splitWithCharCode(pattern.codeUnitAt(0));
+    }
+    return super.split(pattern);
+  }
+}
+
+
+class _TwoByteString extends _StringBase implements String {
+  factory _TwoByteString._uninstantiable() {
+    throw new UnsupportedError(
+        "_TwoByteString can only be allocated by the VM");
+  }
+
+  // Checks for one-byte whitespaces only.
+  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
+  // whitespaces. Add checking for multi-byte whitespace codepoints.
+  bool _isWhitespace(int codePoint) {
+    return
+      (codePoint == 32) || // Space.
+      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
+  }
+}
+
+
+class _FourByteString extends _StringBase implements String {
+  factory _FourByteString._uninstantiable() {
+    throw new UnsupportedError(
+        "_FourByteString can only be allocated by the VM");
+  }
+
+  // Checks for one-byte whitespaces only.
+  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
+  // whitespaces. Add checking for multi-byte whitespace codepoints.
+  bool _isWhitespace(int codePoint) {
+    return
+      (codePoint == 32) || // Space.
+      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
+  }
+}
+
+
+class _ExternalOneByteString extends _StringBase implements String {
+  factory _ExternalOneByteString._uninstantiable() {
+    throw new UnsupportedError(
+        "_ExternalOneByteString can only be allocated by the VM");
+  }
+
+  // Checks for one-byte whitespaces only.
+  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
+  // whitespaces for one byte strings.
+  bool _isWhitespace(int codePoint) {
+    return
+      (codePoint == 32) || // Space.
+      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
+  }
+}
+
+
+class _ExternalTwoByteString extends _StringBase implements String {
+  factory _ExternalTwoByteString._uninstantiable() {
+    throw new UnsupportedError(
+        "_ExternalTwoByteString can only be allocated by the VM");
+  }
+
+  // Checks for one-byte whitespaces only.
+  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
+  // whitespaces. Add checking for multi-byte whitespace codepoints.
+  bool _isWhitespace(int codePoint) {
+    return
+      (codePoint == 32) || // Space.
+      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
+  }
+}
+
+
+class _ExternalFourByteString extends _StringBase implements String {
+  factory _ExternalFourByteString._uninstantiable() {
+    throw new UnsupportedError(
+        "ExternalFourByteString can only be allocated by the VM");
+  }
+
+  // Checks for one-byte whitespaces only.
+  // TODO(srdjan): Investigate if 0x85 (NEL) and 0xA0 (NBSP) are valid
+  // whitespaces. Add checking for multi-byte whitespace codepoints.
+  bool _isWhitespace(int codePoint) {
+    return
+      (codePoint == 32) || // Space.
+      ((9 <= codePoint) && (codePoint <= 13)); // CR, LF, TAB, etc.
+  }
+}
+
+
+class _StringMatch implements Match {
+  const _StringMatch(int this.start,
+                     String this.str,
+                     String this.pattern);
+
+  int get end => start + pattern.length;
+  String operator[](int g) => group(g);
+  int get groupCount => 0;
+
+  String group(int group) {
+    if (group != 0) {
+      throw new RangeError.value(group);
+    }
+    return pattern;
+  }
+
+  List<String> groups(List<int> groups) {
+    List<String> result = new List<String>();
+    for (int g in groups) {
+      result.add(group(g));
+    }
+    return result;
+  }
+
+  final int start;
+  final String str;
+  final String pattern;
+}
diff --git a/runtime/lib/typeddata.cc b/runtime/lib/typeddata.cc
index bf61ba8..d985975 100644
--- a/runtime/lib/typeddata.cc
+++ b/runtime/lib/typeddata.cc
@@ -171,7 +171,6 @@
 
 CLASS_LIST_TYPED_DATA(TYPED_DATA_NEW_NATIVE)
 
-
 #define TYPED_DATA_GETTER(getter, object)                                      \
 DEFINE_NATIVE_ENTRY(TypedData_##getter, 2) {                                   \
   GET_NON_NULL_NATIVE_ARGUMENT(Instance, instance, arguments->NativeArgAt(0)); \
@@ -306,5 +305,6 @@
 TYPED_DATA_UINT64_NATIVES(Uint64Array, GetUint64, SetUint64, Integer)
 TYPED_DATA_NATIVES(Float32Array, GetFloat32, SetFloat32, Double, value)
 TYPED_DATA_NATIVES(Float64Array, GetFloat64, SetFloat64, Double, value)
+TYPED_DATA_NATIVES(Float32x4Array, GetFloat32x4, SetFloat32x4, Float32x4, value)
 
 }  // namespace dart
diff --git a/runtime/lib/typeddata.dart b/runtime/lib/typeddata.dart
index ab40008..4ece1af 100644
--- a/runtime/lib/typeddata.dart
+++ b/runtime/lib/typeddata.dart
@@ -224,6 +224,45 @@
   }
 }
 
+patch class Float32x4List {
+  /* patch */ factory Float32x4List(int length) {
+    return new _Float32x4Array(length);
+  }
+
+  /* patch */ factory Float32x4List.transferable(int length) {
+    return _newTransferable(length);
+  }
+
+  /* patch */ factory Float32x4List.view(ByteBuffer buffer,
+                                         [int offsetInBytes = 0, int length]) {
+    return new _Float32x4ArrayView(buffer, offsetInBytes, length);
+  }
+
+  static _ExternalFloat32x4Array _newTransferable(int length) {
+    return new _ExternalFloat32x4Array(length);
+  }
+}
+
+
+patch class Float32x4 {
+  /* patch */ factory Float32x4(double x, double y, double z, double w) {
+    return new _Float32x4(x, y, z, w);
+  }
+  /* patch */ factory Float32x4.zero() {
+    return new _Float32x4.zero();
+  }
+}
+
+
+patch class Uint32x4 {
+  /* patch */ factory Uint32x4(int x, int y, int z, int w) {
+    return new _Uint32x4(x, y, z, w);
+  }
+  /* patch */ factory Uint32x4.bool(bool x, bool y, bool z, bool w) {
+    return new _Uint32x4.bool(x, y, z, w);
+  }
+}
+
 
 patch class ByteData {
   /* patch */ factory ByteData(int length) {
@@ -523,6 +562,10 @@
   double _getFloat64(int offsetInBytes) native "TypedData_GetFloat64";
   void _setFloat64(int offsetInBytes, double value)
       native "TypedData_SetFloat64";
+
+  Float32x4 _getFloat32x4(int offsetInBytes) native "TypedData_GetFloat32x4";
+  void _setFloat32x4(int offsetInBytes, Float32x4 value)
+      native "TypedData_SetFloat32x4";
 }
 
 
@@ -550,16 +593,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getInt8(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setInt8(index, _toInt8(value));
   }
@@ -609,16 +650,14 @@
   // Methods implementing List interface.
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getUint8(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setUint8(index, _toUint8(value));
   }
@@ -668,16 +707,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getUint8(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setUint8(index, _toClampedUint8(value));
   }
@@ -729,16 +766,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedInt16(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedInt16(index, _toInt16(value));
   }
@@ -798,16 +833,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedUint16(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedUint16(index, _toUint16(value));
   }
@@ -867,16 +900,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedInt32(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedInt32(index, _toInt32(value));
   }
@@ -936,16 +967,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedUint32(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedUint32(index, _toUint32(value));
   }
@@ -1005,16 +1034,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedInt64(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedInt64(index, _toInt64(value));
   }
@@ -1074,16 +1101,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedUint64(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedUint64(index, _toUint64(value));
   }
@@ -1143,16 +1168,14 @@
 
   double operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedFloat32(index);
   }
 
   void operator[]=(int index, double value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedFloat32(index, value);
   }
@@ -1212,16 +1235,14 @@
 
   double operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedFloat64(index);
   }
 
   void operator[]=(int index, double value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedFloat64(index, value);
   }
@@ -1255,6 +1276,70 @@
   static _Float64Array _new(int length) native "TypedData_Float64Array_new";
 }
 
+class _Float32x4Array extends _TypedList implements Float32x4List {
+  // Factory constructors.
+
+  factory _Float32x4Array(int length) {
+    if (length < 0) {
+      String message = "$length must be greater than 0";
+      throw new ArgumentError(message);
+    }
+    return _new(length);
+  }
+
+  factory _Float32x4Array.view(ByteBuffer buffer,
+                               [int offsetInBytes = 0, int length]) {
+    if (length == null) {
+      length = (buffer.lengthInBytes - offsetInBytes) ~/
+               Float32x4List.BYTES_PER_ELEMENT;
+    }
+    return new _Float32x4ArrayView(buffer, offsetInBytes, length);
+  }
+
+
+  Float32x4 operator[](int index) {
+    if (index < 0 || index >= length) {
+      _throwRangeError(index, length);
+    }
+    return _getIndexedFloat32x4(index);
+  }
+
+  void operator[]=(int index, Float32x4 value) {
+    if (index < 0 || index >= length) {
+      _throwRangeError(index, length);
+    }
+    _setIndexedFloat32x4(index, value);
+  }
+
+  Iterator<Float32x4> get iterator {
+    return new _TypedListIterator<Float32x4>(this);
+  }
+
+
+  // Method(s) implementing the TypedData interface.
+
+  int get elementSizeInBytes {
+    return Float32x4List.BYTES_PER_ELEMENT;
+  }
+
+
+  // Internal utility methods.
+
+  _Float32x4Array _createList(int length) {
+    return _new(length);
+  }
+
+  Float32x4 _getIndexedFloat32x4(int index) {
+    return _getFloat32x4(index * Float32x4List.BYTES_PER_ELEMENT);
+  }
+
+  void _setIndexedFloat32x4(int index, Float32x4 value) {
+    _setFloat32x4(index * Float32x4List.BYTES_PER_ELEMENT, value);
+  }
+
+  static _Float32x4Array _new(int length) native "TypedData_Float32x4Array_new";
+}
+
 
 class _ExternalInt8Array extends _TypedList implements Int8List {
   // Factory constructors.
@@ -1271,16 +1356,14 @@
   // Method(s) implementing the List interface.
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getInt8(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setInt8(index, value);
   }
@@ -1324,16 +1407,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getUint8(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setUint8(index, _toUint8(value));
   }
@@ -1377,16 +1458,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getUint8(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setUint8(index, _toClampedUint8(value));
   }
@@ -1430,16 +1509,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedInt16(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedInt16(index, _toInt16(value));
   }
@@ -1491,16 +1568,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedUint16(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedUint16(index, _toUint16(value));
   }
@@ -1552,16 +1627,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedInt32(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedInt32(index, _toInt32(value));
   }
@@ -1613,16 +1686,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedUint32(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedUint32(index, _toUint32(value));
   }
@@ -1674,16 +1745,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedInt64(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedInt64(index, _toInt64(value));
   }
@@ -1735,16 +1804,14 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedUint64(index);
   }
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedUint64(index, _toUint64(value));
   }
@@ -1796,16 +1863,14 @@
 
   double operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedFloat32(index);
   }
 
   void operator[]=(int index, double value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedFloat32(index, value);
   }
@@ -1857,16 +1922,14 @@
 
   double operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _getIndexedFloat64(index);
   }
 
   void operator[]=(int index, double value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _setIndexedFloat64(index, value);
   }
@@ -1902,6 +1965,215 @@
 }
 
 
+class _ExternalFloat32x4Array extends _TypedList implements Float32x4List {
+  // Factory constructors.
+
+  factory _ExternalFloat32x4Array(int length) {
+    if (length < 0) {
+      String message = "$length must be greater than 0";
+      throw new ArgumentError(message);
+    }
+    return _new(length);
+  }
+
+
+  // Method(s) implementing the List interface.
+
+  Float32x4 operator[](int index) {
+    if (index < 0 || index >= length) {
+      _throwRangeError(index, length);
+    }
+    return _getIndexedFloat32x4(index);
+  }
+
+  void operator[]=(int index, Float32x4 value) {
+    if (index < 0 || index >= length) {
+      _throwRangeError(index, length);
+    }
+    _setIndexedFloat32x4(index, value);
+  }
+
+  Iterator<Float32x4> get iterator {
+    return new _TypedListIterator<Float32x4>(this);
+  }
+
+
+  // Method(s) implementing the TypedData interface.
+
+  int get elementSizeInBytes {
+    return Float32x4List.BYTES_PER_ELEMENT;
+  }
+
+
+  // Internal utility methods.
+
+  Float32x4List _createList(int length) {
+    return new Float32x4List(length);
+  }
+
+  Float32x4 _getIndexedFloat32x4(int index) {
+    return _getFloat32x4(index * Float32x4List.BYTES_PER_ELEMENT);
+  }
+
+  void _setIndexedFloat32x4(int index, Float32x4 value) {
+    _setFloat32x4(index * Float32x4List.BYTES_PER_ELEMENT, value);
+  }
+
+  static _ExternalFloat32x4Array _new(int length) native
+      "ExternalTypedData_Float32x4Array_new";
+}
+
+
+class _Float32x4 implements Float32x4 {
+  factory _Float32x4(double x, double y, double z, double w)
+      native "Float32x4_fromDoubles";
+  factory _Float32x4.zero() native "Float32x4_zero";
+  Float32x4 operator +(Float32x4 other) {
+    return _add(other);
+  }
+  Float32x4 _add(Float32x4 other) native "Float32x4_add";
+  Float32x4 operator -() {
+    return _negate();
+  }
+  Float32x4 _negate() native "Float32x4_negate";
+  Float32x4 operator -(Float32x4 other) {
+    return _sub(other);
+  }
+  Float32x4 _sub(Float32x4 other) native "Float32x4_sub";
+  Float32x4 operator *(Float32x4 other) {
+    return _mul(other);
+  }
+  Float32x4 _mul(Float32x4 other) native "Float32x4_mul";
+  Float32x4 operator /(Float32x4 other) {
+    return _div(other);
+  }
+  Float32x4 _div(Float32x4 other) native "Float32x4_div";
+  Uint32x4 lessThan(Float32x4 other) {
+    return _cmplt(other);
+  }
+  Uint32x4 _cmplt(Float32x4 other) native "Float32x4_cmplt";
+  Uint32x4 lessThanOrEqual(Float32x4 other) {
+    return _cmplte(other);
+  }
+  Uint32x4 _cmplte(Float32x4 other) native "Float32x4_cmplte";
+  Uint32x4 greaterThan(Float32x4 other) {
+    return _cmpgt(other);
+  }
+  Uint32x4 _cmpgt(Float32x4 other) native "Float32x4_cmpgt";
+  Uint32x4 greaterThanOrEqual(Float32x4 other) {
+    return _cmpgte(other);
+  }
+  Uint32x4 _cmpgte(Float32x4 other) native "Float32x4_cmpgte";
+  Uint32x4 equal(Float32x4 other) {
+    return _cmpequal(other);
+  }
+  Uint32x4 _cmpequal(Float32x4 other)
+      native "Float32x4_cmpequal";
+  Uint32x4 notEqual(Float32x4 other) {
+    return _cmpnequal(other);
+  }
+  Uint32x4 _cmpnequal(Float32x4 other)
+      native "Float32x4_cmpnequal";
+  Float32x4 scale(double s) {
+    return _scale(s);
+  }
+  Float32x4 _scale(double s) native "Float32x4_scale";
+  Float32x4 abs() {
+    return _abs();
+  }
+  Float32x4 _abs() native "Float32x4_abs";
+  Float32x4 clamp(Float32x4 lowerLimit,
+                         Float32x4 upperLimit) {
+    return _clamp(lowerLimit, upperLimit);
+  }
+  Float32x4 _clamp(Float32x4 lowerLimit,
+                          Float32x4 upperLimit)
+      native "Float32x4_clamp";
+  double get x native "Float32x4_getX";
+  double get y native "Float32x4_getY";
+  double get z native "Float32x4_getZ";
+  double get w native "Float32x4_getW";
+  Float32x4 get xxxx native "Float32x4_getXXXX";
+  Float32x4 get yyyy native "Float32x4_getYYYY";
+  Float32x4 get zzzz native "Float32x4_getZZZZ";
+  Float32x4 get wwww native "Float32x4_getWWWW";
+  Float32x4 withX(double x) native "Float32x4_setX";
+  Float32x4 withY(double y) native "Float32x4_setY";
+  Float32x4 withZ(double z) native "Float32x4_setZ";
+  Float32x4 withW(double w) native "Float32x4_setW";
+  Float32x4 min(Float32x4 other) {
+    return _min(other);
+  }
+  Float32x4 _min(Float32x4 other) native "Float32x4_min";
+  Float32x4 max(Float32x4 other) {
+    return _max(other);
+  }
+  Float32x4 _max(Float32x4 other) native "Float32x4_max";
+  Float32x4 sqrt() {
+    return _sqrt();
+  }
+  Float32x4 _sqrt() native "Float32x4_sqrt";
+  Float32x4 reciprocal() {
+    return _reciprocal();
+  }
+  Float32x4 _reciprocal() native "Float32x4_reciprocal";
+  Float32x4 reciprocalSqrt() {
+    return _reciprocalSqrt();
+  }
+  Float32x4 _reciprocalSqrt() native "Float32x4_reciprocalSqrt";
+  Uint32x4 toUint32x4() {
+      return _toUint32x4();
+  }
+  Uint32x4 _toUint32x4() native "Float32x4_toUint32x4";
+}
+
+
+class _Uint32x4 implements Uint32x4 {
+  factory _Uint32x4(int x, int y, int z, int w)
+      native "Uint32x4_fromInts";
+  factory _Uint32x4.bool(bool x, bool y, bool z, bool w)
+      native "Uint32x4_fromBools";
+  Uint32x4 operator |(Uint32x4 other) {
+    return _or(other);
+  }
+  Uint32x4 _or(Uint32x4 other) native "Uint32x4_or";
+  Uint32x4 operator &(Uint32x4 other) {
+    return _and(other);
+  }
+  Uint32x4 _and(Uint32x4 other) native "Uint32x4_and";
+  Uint32x4 operator ^(Uint32x4 other) {
+    return _xor(other);
+  }
+  Uint32x4 _xor(Uint32x4 other) native "Uint32x4_xor";
+  int get x native "Uint32x4_getX";
+  int get y native "Uint32x4_getY";
+  int get z native "Uint32x4_getZ";
+  int get w native "Uint32x4_getW";
+  Uint32x4 withX(int x) native "Uint32x4_setX";
+  Uint32x4 withY(int y) native "Uint32x4_setY";
+  Uint32x4 withZ(int z) native "Uint32x4_setZ";
+  Uint32x4 withW(int w) native "Uint32x4_setW";
+  bool get flagX native "Uint32x4_getFlagX";
+  bool get flagY native "Uint32x4_getFlagY";
+  bool get flagZ native "Uint32x4_getFlagZ";
+  bool get flagW native "Uint32x4_getFlagW";
+  Uint32x4 withFlagX(bool x) native "Uint32x4_setFlagX";
+  Uint32x4 withFlagY(bool y) native "Uint32x4_setFlagY";
+  Uint32x4 withFlagZ(bool z) native "Uint32x4_setFlagZ";
+  Uint32x4 withFlagW(bool w) native "Uint32x4_setFlagW";
+  Float32x4 select(Float32x4 trueValue,
+                          Float32x4 falseValue) {
+    return _select(trueValue, falseValue);
+  }
+  Float32x4 _select(Float32x4 trueValue,
+                           Float32x4 falseValue)
+      native "Uint32x4_select";
+  Float32x4 toFloat32x4() {
+      return _toFloat32x4();
+  }
+  Float32x4 _toFloat32x4() native "Uint32x4_toFloat32x4";
+}
+
 class _TypedListIterator<E> implements Iterator<E> {
   final List<E> _array;
   final int _length;
@@ -1962,7 +2234,7 @@
                             Int8List.BYTES_PER_ELEMENT))) {
     _rangeCheck(buffer.lengthInBytes,
                 _offsetInBytes,
-                _length * Int8List.BYTES_PER_ELEMENT);
+                length * Int8List.BYTES_PER_ELEMENT);
   }
 
 
@@ -1970,8 +2242,7 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _typeddata._getInt8(offsetInBytes +
                                (index * Int8List.BYTES_PER_ELEMENT));
@@ -1979,10 +2250,9 @@
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
-    _typeddata. setInt8(offsetInBytes + (index * Int8List.BYTES_PER_ELEMENT),
+    _typeddata._setInt8(offsetInBytes + (index * Int8List.BYTES_PER_ELEMENT),
                         _toInt8(value));
   }
 
@@ -1996,6 +2266,13 @@
   int get elementSizeInBytes {
     return Int8List.BYTES_PER_ELEMENT;
   }
+
+
+  // Internal utility methods.
+
+  Int8List _createList(int length) {
+    return new Int8List(length);
+  }
 }
 
 
@@ -2008,7 +2285,7 @@
                             Uint8List.BYTES_PER_ELEMENT))) {
     _rangeCheck(buffer.lengthInBytes,
                 _offsetInBytes,
-                _length * Uint8List.BYTES_PER_ELEMENT);
+                length * Uint8List.BYTES_PER_ELEMENT);
   }
 
 
@@ -2016,8 +2293,7 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _typeddata._getUint8(offsetInBytes +
                                 (index * Uint8List.BYTES_PER_ELEMENT));
@@ -2025,8 +2301,7 @@
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _typeddata._setUint8(offsetInBytes + (index * Uint8List.BYTES_PER_ELEMENT),
                          _toUint8(value));
@@ -2042,6 +2317,13 @@
   int get elementSizeInBytes {
     return Uint8List.BYTES_PER_ELEMENT;
   }
+
+
+  // Internal utility methods.
+
+  Uint8List _createList(int length) {
+    return new Uint8List(length);
+  }
 }
 
 
@@ -2063,8 +2345,7 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _typeddata._getUint8(offsetInBytes +
                                 (index * Uint8List.BYTES_PER_ELEMENT));
@@ -2072,8 +2353,7 @@
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _typeddata._setUint8(offsetInBytes + (index * Uint8List.BYTES_PER_ELEMENT),
                          _toClampedUint8(value));
@@ -2089,6 +2369,13 @@
   int get elementSizeInBytes {
     return Uint8List.BYTES_PER_ELEMENT;
   }
+
+
+  // Internal utility methods.
+
+  Uint8ClampedList _createList(int length) {
+    return new Uint8ClampedList(length);
+  }
 }
 
 
@@ -2109,8 +2396,7 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _typeddata._getInt16(offsetInBytes +
                                 (index * Int16List.BYTES_PER_ELEMENT));
@@ -2118,8 +2404,7 @@
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _typeddata._setInt16(offsetInBytes + (index * Int16List.BYTES_PER_ELEMENT),
                          _toInt16(value));
@@ -2135,6 +2420,13 @@
   int get elementSizeInBytes {
     return Int16List.BYTES_PER_ELEMENT;
   }
+
+
+  // Internal utility methods.
+
+  Int16List _createList(int length) {
+    return new Int16List(length);
+  }
 }
 
 
@@ -2155,8 +2447,7 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _typeddata._getUint16(offsetInBytes +
                                  (index * Uint16List.BYTES_PER_ELEMENT));
@@ -2164,8 +2455,7 @@
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _typeddata._setUint16(offsetInBytes + (index * Uint16List.BYTES_PER_ELEMENT),
                           _toUint16(value));
@@ -2181,6 +2471,13 @@
   int get elementSizeInBytes {
     return Uint16List.BYTES_PER_ELEMENT;
   }
+
+
+  // Internal utility methods.
+
+  Uint16List _createList(int length) {
+    return new Uint16List(length);
+  }
 }
 
 
@@ -2201,8 +2498,7 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _typeddata._getInt32(offsetInBytes +
                                 (index * Int32List.BYTES_PER_ELEMENT));
@@ -2210,8 +2506,7 @@
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _typeddata._setInt32(offsetInBytes + (index * Int32List.BYTES_PER_ELEMENT),
                          _toInt32(value));
@@ -2227,6 +2522,13 @@
   int get elementSizeInBytes {
     return Int32List.BYTES_PER_ELEMENT;
   }
+
+
+  // Internal utility methods.
+
+  Int32List _createList(int length) {
+    return new Int32List(length);
+  }
 }
 
 
@@ -2247,8 +2549,7 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _typeddata._getUint32(offsetInBytes +
                                  (index * Uint32List.BYTES_PER_ELEMENT));
@@ -2256,8 +2557,7 @@
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _typeddata._setUint32(offsetInBytes + (index * Uint32List.BYTES_PER_ELEMENT),
                           _toUint32(value));
@@ -2273,6 +2573,13 @@
   int get elementSizeInBytes {
     return Uint32List.BYTES_PER_ELEMENT;
   }
+
+
+  // Internal utility methods.
+
+  Uint32List _createList(int length) {
+    return new Uint32List(length);
+  }
 }
 
 
@@ -2293,8 +2600,7 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _typeddata._getInt64(offsetInBytes +
                                 (index * Int64List.BYTES_PER_ELEMENT));
@@ -2302,8 +2608,7 @@
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _typeddata._setInt64(offsetInBytes + (index * Int64List.BYTES_PER_ELEMENT),
                          _toInt64(value));
@@ -2319,6 +2624,13 @@
   int get elementSizeInBytes {
     return Int64List.BYTES_PER_ELEMENT;
   }
+
+
+  // Internal utility methods.
+
+  Int64List _createList(int length) {
+    return new Int64List(length);
+  }
 }
 
 
@@ -2339,8 +2651,7 @@
 
   int operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _typeddata._getUint64(offsetInBytes +
                                  (index * Uint64List.BYTES_PER_ELEMENT));
@@ -2348,8 +2659,7 @@
 
   void operator[]=(int index, int value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _typeddata._setUint64(offsetInBytes + (index * Uint64List.BYTES_PER_ELEMENT),
                           _toUint64(value));
@@ -2365,6 +2675,13 @@
   int get elementSizeInBytes {
     return Uint64List.BYTES_PER_ELEMENT;
   }
+
+
+  // Internal utility methods.
+
+  Uint64List _createList(int length) {
+    return new Uint64List(length);
+  }
 }
 
 
@@ -2385,8 +2702,7 @@
 
   double operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _typeddata._getFloat32(offsetInBytes +
                                   (index * Float32List.BYTES_PER_ELEMENT));
@@ -2394,8 +2710,7 @@
 
   void operator[]=(int index, double value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _typeddata._setFloat32(offsetInBytes +
                            (index * Float32List.BYTES_PER_ELEMENT), value);
@@ -2411,6 +2726,13 @@
   int get elementSizeInBytes {
     return Float32List.BYTES_PER_ELEMENT;
   }
+
+
+  // Internal utility methods.
+
+  Float32List _createList(int length) {
+    return new Float32List(length);
+  }
 }
 
 
@@ -2431,8 +2753,7 @@
 
   double operator[](int index) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     return _typeddata._getFloat64(offsetInBytes +
                                   (index * Float64List.BYTES_PER_ELEMENT));
@@ -2440,8 +2761,7 @@
 
   void operator[]=(int index, double value) {
     if (index < 0 || index >= length) {
-      String message = "$index must be in the range [0..$length)";
-      throw new RangeError(message);
+      _throwRangeError(index, length);
     }
     _typeddata._setFloat64(offsetInBytes +
                           (index * Float64List.BYTES_PER_ELEMENT), value);
@@ -2457,15 +2777,73 @@
   int get elementSizeInBytes {
     return Float64List.BYTES_PER_ELEMENT;
   }
+
+
+  // Internal utility methods.
+
+  Float64List _createList(int length) {
+    return new Float64List(length);
+  }
+}
+
+
+class _Float32x4ArrayView extends _TypedListView implements Float32x4List {
+  // Constructor.
+  _Float32x4ArrayView(ByteBuffer buffer, [int _offsetInBytes = 0, int _length])
+    : super(buffer, _offsetInBytes,
+            _defaultIfNull(_length,
+                           ((buffer.lengthInBytes - _offsetInBytes) ~/
+                            Float32x4List.BYTES_PER_ELEMENT))) {
+    _rangeCheck(buffer.lengthInBytes,
+                offsetInBytes,
+                length * Float32x4List.BYTES_PER_ELEMENT);
+  }
+
+
+  // Method(s) implementing List interface.
+
+  Float32x4 operator[](int index) {
+    if (index < 0 || index >= length) {
+      _throwRangeError(index, length);
+    }
+    return _typeddata._getFloat32x4(offsetInBytes +
+                                  (index * Float32x4List.BYTES_PER_ELEMENT));
+  }
+
+  void operator[]=(int index, Float32x4 value) {
+    if (index < 0 || index >= length) {
+      _throwRangeError(index, length);
+    }
+    _typeddata._setFloat32x4(offsetInBytes +
+                             (index * Float32x4List.BYTES_PER_ELEMENT), value);
+  }
+
+  Iterator<Float32x4> get iterator {
+    return new _TypedListIterator<Float32x4>(this);
+  }
+
+
+  // Method(s) implementing TypedData interface.
+
+  int get elementSizeInBytes {
+    return Float32x4List.BYTES_PER_ELEMENT;
+  }
+
+
+  // Internal utility methods.
+
+  Float32x4List _createList(int length) {
+    return new Float32x4List(length);
+  }
 }
 
 
 class _ByteDataView implements ByteData {
   _ByteDataView(ByteBuffer _buffer, int _offsetInBytes, int _lengthInBytes)
-    : _typeddata = _buffer as TypedData,
+    : _typeddata = _buffer,  // _buffer is guaranteed to be a TypedData here.
       _offset = _offsetInBytes,
-      _length = _lengthInBytes {
-    _rangeCheck(_buffer.lengthInBytes, _offset, _length);
+      length = _lengthInBytes {
+    _rangeCheck(_buffer.lengthInBytes, _offset, length);
   }
 
 
@@ -2476,88 +2854,162 @@
   }
 
   int get lengthInBytes {
-    return _length;
+    return length;
   }
 
-  int offsetInBytes() {
+  int get offsetInBytes {
     return _offset;
   }
 
   // Method(s) implementing ByteData interface.
 
   int getInt8(int byteOffset) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     return _typeddata._getInt8(_offset + byteOffset);
   }
   void setInt8(int byteOffset, int value) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     _typeddata._setInt8(_offset + byteOffset, value);
   }
 
   int getUint8(int byteOffset) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     return _typeddata._getUint8(_offset + byteOffset);
   }
   void setUint8(int byteOffset, int value) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     _typeddata._setUint8(_offset + byteOffset, value);
   }
 
   int getInt16(int byteOffset) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     return _typeddata._getInt16(_offset + byteOffset);
   }
   void setInt16(int byteOffset, int value) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     _typeddata._setInt16(_offset + byteOffset, value);
   }
 
   int getUint16(int byteOffset) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     return _typeddata._getUint16(_offset + byteOffset);
   }
   void setUint16(int byteOffset, int value) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     _typeddata._setUint16(_offset + byteOffset, value);
   }
 
   int getInt32(int byteOffset) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     return _typeddata._getInt32(_offset + byteOffset);
   }
   void setInt32(int byteOffset, int value) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     _typeddata._setInt32(_offset + byteOffset, value);
   }
 
   int getUint32(int byteOffset) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     return _typeddata._getUint32(_offset + byteOffset);
   }
   void setUint32(int byteOffset, int value) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     _typeddata._setUint32(_offset + byteOffset, value);
   }
 
   int getInt64(int byteOffset) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     return _typeddata._getInt64(_offset + byteOffset);
   }
   void setInt64(int byteOffset, int value) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     _typeddata._setInt64(_offset + byteOffset, value);
   }
 
   int getUint64(int byteOffset) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     return _typeddata._getUint64(_offset + byteOffset);
   }
   void setUint64(int byteOffset, int value) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     _typeddata._setUint64(_offset + byteOffset, value);
   }
 
   double getFloat32(int byteOffset) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     return _typeddata._getFloat32(_offset + byteOffset);
   }
   void setFloat32(int byteOffset, double value) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     _typeddata._setFloat32(_offset + byteOffset, value);
   }
 
   double getFloat64(int byteOffset) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     return _typeddata._getFloat64(_offset + byteOffset);
   }
   void setFloat64(int byteOffset, double value) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
     _typeddata._setFloat64(_offset + byteOffset, value);
   }
 
+  Float32x4 getFloat32x4(int byteOffset) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
+    return _typeddata._getFloat32x4(_offset + byteOffset);
+  }
+  void setFloat32x4(int byteOffset, Float32x4 value) {
+    if (byteOffset < 0 || byteOffset >= length) {
+      _throwRangeError(byteOffset, length);
+    }
+    _typeddata._setFloat32x4(_offset + byteOffset, value);
+
+  }
+
   final TypedData _typeddata;
   final int _offset;
-  final int _length;
+  final int length;
 }
 
 
@@ -2635,3 +3087,9 @@
   }
   return object;
 }
+
+
+void _throwRangeError(int index, int length) {
+  String message = "$index must be in the range [0..$length)";
+  throw new RangeError(message);
+}
diff --git a/runtime/lib/typeddata_sources.gypi b/runtime/lib/typeddata_sources.gypi
index 05be7c3..fc5ba11 100644
--- a/runtime/lib/typeddata_sources.gypi
+++ b/runtime/lib/typeddata_sources.gypi
@@ -8,6 +8,7 @@
   'sources': [
     'typeddata.cc',
     'typeddata.dart',
+    'simd128.cc',
   ],
 }
 
diff --git a/runtime/platform/json.cc b/runtime/platform/json.cc
index 7236e74..899b62c 100644
--- a/runtime/platform/json.cc
+++ b/runtime/platform/json.cc
@@ -545,6 +545,19 @@
 }
 
 
+void TextBuffer::AddString(const char* s) {
+  Printf("%s", s);
+}
+
+
+void TextBuffer::AddEscapedString(const char* s) {
+  intptr_t len = strlen(s);
+  for (int i = 0; i < len; i++) {
+    AddEscapedChar(s[i]);
+  }
+}
+
+
 void TextBuffer::EnsureCapacity(intptr_t len) {
   intptr_t remaining = buf_size_ - msg_len_;
   if (remaining <= len) {
diff --git a/runtime/platform/json.h b/runtime/platform/json.h
index f2e0752..5ab5909 100644
--- a/runtime/platform/json.h
+++ b/runtime/platform/json.h
@@ -127,6 +127,8 @@
   void AddChar(char ch);
   void AddUTF8(uint32_t ch);
   void AddEscapedChar(uint32_t ch);
+  void AddString(const char* s);
+  void AddEscapedString(const char* s);
 
   void Clear();
 
diff --git a/runtime/tests/vm/dart/byte_array_optimized_test.dart b/runtime/tests/vm/dart/byte_array_optimized_test.dart
index e645c733..153ebc39 100644
--- a/runtime/tests/vm/dart/byte_array_optimized_test.dart
+++ b/runtime/tests/vm/dart/byte_array_optimized_test.dart
@@ -5,7 +5,7 @@
 // Library tag to be able to run in html test framework.
 library byte_array_test;
 
-import 'dart:scalarlist';
+import 'dart:typeddata';
 
 // This test exercises optimized [] and []= operators
 // on byte array views.
@@ -13,8 +13,8 @@
   static testInt8ListImpl(Int8List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(10, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(10, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -100,8 +100,8 @@
   static testUint8ListImpl(Uint8List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(10, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(10, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -176,8 +176,8 @@
   static testInt16ListImpl(Int16List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(2, array.bytesPerElement());
-    Expect.equals(20, array.lengthInBytes());
+    Expect.equals(2, array.elementSizeInBytes);
+    Expect.equals(20, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -264,8 +264,8 @@
   static testUint16ListImpl(Uint16List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(2, array.bytesPerElement());
-    Expect.equals(20, array.lengthInBytes());
+    Expect.equals(2, array.elementSizeInBytes);
+    Expect.equals(20, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -340,8 +340,8 @@
   static testInt32ListImpl(Int32List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(4, array.bytesPerElement());
-    Expect.equals(40, array.lengthInBytes());
+    Expect.equals(4, array.elementSizeInBytes);
+    Expect.equals(40, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -434,8 +434,8 @@
   static testUint32ListImpl(Uint32List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(4, array.bytesPerElement());
-    Expect.equals(40, array.lengthInBytes());
+    Expect.equals(4, array.elementSizeInBytes);
+    Expect.equals(40, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -516,8 +516,8 @@
   static testInt64ListImpl(Int64List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(8, array.bytesPerElement());
-    Expect.equals(80, array.lengthInBytes());
+    Expect.equals(8, array.elementSizeInBytes);
+    Expect.equals(80, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -611,8 +611,8 @@
   static testUint64ListImpl(Uint64List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(8, array.bytesPerElement());
-    Expect.equals(80, array.lengthInBytes());
+    Expect.equals(8, array.elementSizeInBytes);
+    Expect.equals(80, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -690,8 +690,8 @@
   static testFloat32ListImpl(Float32List array) {
     Expect.isTrue(array is List<double>);
     Expect.equals(10, array.length);
-    Expect.equals(4, array.bytesPerElement());
-    Expect.equals(40, array.lengthInBytes());
+    Expect.equals(4, array.elementSizeInBytes);
+    Expect.equals(40, array.lengthInBytes);
     Expect.listEquals([0.0, 0.0, 0.0, 0.0, 0.0,
                        0.0, 0.0, 0.0, 0.0, 0.0],
                       array);
@@ -756,8 +756,8 @@
   static testFloat64ListImpl(Float64List array) {
     Expect.isTrue(array is List<double>);
     Expect.equals(10, array.length);
-    Expect.equals(8, array.bytesPerElement());
-    Expect.equals(80, array.lengthInBytes());
+    Expect.equals(8, array.elementSizeInBytes);
+    Expect.equals(80, array.lengthInBytes);
     Expect.listEquals([0.0, 0.0, 0.0, 0.0, 0.0,
                        0.0, 0.0, 0.0, 0.0, 0.0],
                       array);
@@ -821,39 +821,39 @@
 
   static testInt8ListViewImpl(var array) {
     Expect.equals(12, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(12, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(12, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xFF;
     }
-    Expect.throws(() { new Int8List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Int8List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int8List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Int8List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int8List.view(array.asByteArray(),
-                                         array.lengthInBytes() + 1); },
+    Expect.throws(() { new Int8List.view(array.buffer,
+                                         array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int8List.view(array.asByteArray(),
+    Expect.throws(() { new Int8List.view(array.buffer,
                                          0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int8List.view(array.asByteArray(),
+    Expect.throws(() { new Int8List.view(array.buffer,
                                          array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Int8List.view(array.asByteArray(),
-                                  array.lengthInBytes());
+    var empty = new Int8List.view(array.buffer,
+                                  array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Int8List);
     Expect.equals(0, empty.length);
-    var whole = new Int8List.view(array.asByteArray());
+    var whole = new Int8List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Int8List);
     Expect.equals(12, whole.length);
-    var view = new Int8List.view(array.asByteArray(), 1, array.length - 2);
+    var view = new Int8List.view(array.buffer, 1, array.length - 2);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Int8List);
     Expect.equals(10, view.length);
-    Expect.equals(1, view.bytesPerElement());
-    Expect.equals(10, view.lengthInBytes());
+    Expect.equals(1, view.elementSizeInBytes);
+    Expect.equals(10, view.lengthInBytes);
     Expect.listEquals([-1, -1, -1, -1, -1,
                        -1, -1, -1, -1, -1],
                       view);
@@ -952,39 +952,39 @@
   static testUint8ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(12, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(12, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(12, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = -1;
     }
-    Expect.throws(() { new Uint8List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Uint8List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint8List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Uint8List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint8List.view(array.asByteArray(),
-                                          array.lengthInBytes() + 1); },
+    Expect.throws(() { new Uint8List.view(array.buffer,
+                                          array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint8List.view(array.asByteArray(),
+    Expect.throws(() { new Uint8List.view(array.buffer,
                                           0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint8List.view(array.asByteArray(),
+    Expect.throws(() { new Uint8List.view(array.buffer,
                                           array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Uint8List.view(array.asByteArray(),
-                                   array.lengthInBytes());
+    var empty = new Uint8List.view(array.buffer,
+                                   array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Uint8List);
     Expect.equals(0, empty.length);
-    var whole = new Uint8List.view(array.asByteArray());
+    var whole = new Uint8List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Uint8List);
     Expect.equals(12, whole.length);
-    var view = new Uint8List.view(array.asByteArray(), 1, array.length - 2);
+    var view = new Uint8List.view(array.buffer, 1, array.length - 2);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Uint8List);
     Expect.equals(10, view.length);
-    Expect.equals(1, view.bytesPerElement());
-    Expect.equals(10, view.lengthInBytes());
+    Expect.equals(1, view.elementSizeInBytes);
+    Expect.equals(10, view.lengthInBytes);
     Expect.listEquals([0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
                        0xFF, 0xFF, 0xFF, 0xFF, 0xFF],
                       view);
@@ -1063,39 +1063,39 @@
 
   static testInt16ListViewImpl(var array) {
     Expect.equals(24, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(24, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(24, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xFF;
     }
-    Expect.throws(() { new Int16List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Int16List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int16List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Int16List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int16List.view(array.asByteArray(),
-                                          array.lengthInBytes() + 1); },
+    Expect.throws(() { new Int16List.view(array.buffer,
+                                          array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int16List.view(array.asByteArray(),
+    Expect.throws(() { new Int16List.view(array.buffer,
                                            0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int16List.view(array.asByteArray(),
+    Expect.throws(() { new Int16List.view(array.buffer,
                                            array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Int16List.view(array.asByteArray(),
-                                   array.lengthInBytes());
+    var empty = new Int16List.view(array.buffer,
+                                   array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Int16List);
     Expect.equals(0, empty.length);
-    var whole = new Int16List.view(array.asByteArray());
+    var whole = new Int16List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Int16List);
     Expect.equals(12, whole.length);
-    var view = new Int16List.view(array.asByteArray(), 2, 10);
+    var view = new Int16List.view(array.buffer, 2, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Int16List);
     Expect.equals(10, view.length);
-    Expect.equals(2, view.bytesPerElement());
-    Expect.equals(20, view.lengthInBytes());
+    Expect.equals(2, view.elementSizeInBytes);
+    Expect.equals(20, view.lengthInBytes);
     Expect.listEquals([-1, -1, -1, -1, -1,
                        -1, -1, -1, -1, -1],
                       view);
@@ -1202,39 +1202,39 @@
   static testUint16ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(24, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(24, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(24, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = -1;
     }
-    Expect.throws(() { new Uint16List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Uint16List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint16List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Uint16List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint16List.view(array.asByteArray(),
-                                           array.lengthInBytes() + 1); },
+    Expect.throws(() { new Uint16List.view(array.buffer,
+                                           array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint16List.view(array.asByteArray(),
+    Expect.throws(() { new Uint16List.view(array.buffer,
                                            0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint16List.view(array.asByteArray(),
+    Expect.throws(() { new Uint16List.view(array.buffer,
                                            array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Uint16List.view(array.asByteArray(),
-                                    array.lengthInBytes());
+    var empty = new Uint16List.view(array.buffer,
+                                    array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Uint16List);
     Expect.equals(0, empty.length);
-    var whole = new Uint16List.view(array.asByteArray());
+    var whole = new Uint16List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Uint16List);
     Expect.equals(12, whole.length);
-    var view = new Uint16List.view(array.asByteArray(), 2, 10);
+    var view = new Uint16List.view(array.buffer, 2, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Uint16List);
     Expect.equals(10, view.length);
-    Expect.equals(2, view.bytesPerElement());
-    Expect.equals(20, view.lengthInBytes());
+    Expect.equals(2, view.elementSizeInBytes);
+    Expect.equals(20, view.lengthInBytes);
     Expect.listEquals([0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF,
                        0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF],
                       view);
@@ -1319,39 +1319,39 @@
   static testInt32ListView() {
     var array = new Uint8List(48);
     Expect.equals(48, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(48, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(48, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xFF;
     }
-    Expect.throws(() { new Int32List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Int32List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int32List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Int32List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int32List.view(array.asByteArray(),
-                                          array.lengthInBytes() + 1); },
+    Expect.throws(() { new Int32List.view(array.buffer,
+                                          array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int32List.view(array.asByteArray(),
+    Expect.throws(() { new Int32List.view(array.buffer,
                                           0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int32List.view(array.asByteArray(),
+    Expect.throws(() { new Int32List.view(array.buffer,
                                           array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Int32List.view(array.asByteArray(),
-                                   array.lengthInBytes());
+    var empty = new Int32List.view(array.buffer,
+                                   array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Int32List);
     Expect.equals(0, empty.length);
-    var whole = new Int32List.view(array.asByteArray());
+    var whole = new Int32List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Int32List);
     Expect.equals(12, whole.length);
-    var view = new Int32List.view(array.asByteArray(), 4, 10);
+    var view = new Int32List.view(array.buffer, 4, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Int32List);
     Expect.equals(10, view.length);
-    Expect.equals(4, view.bytesPerElement());
-    Expect.equals(40, view.lengthInBytes());
+    Expect.equals(4, view.elementSizeInBytes);
+    Expect.equals(40, view.lengthInBytes);
     Expect.listEquals([-1, -1, -1, -1, -1,
                        -1, -1, -1, -1, -1],
                       view);
@@ -1477,39 +1477,39 @@
   static testUint32ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(48, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(48, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(48, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = -1;
     }
-    Expect.throws(() { new Uint32List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Uint32List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint32List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Uint32List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint32List.view(array.asByteArray(),
-                                           array.lengthInBytes() + 1); },
+    Expect.throws(() { new Uint32List.view(array.buffer,
+                                           array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint32List.view(array.asByteArray(),
+    Expect.throws(() { new Uint32List.view(array.buffer,
                                            0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint32List.view(array.asByteArray(),
+    Expect.throws(() { new Uint32List.view(array.buffer,
                                            array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Uint32List.view(array.asByteArray(),
-                                    array.lengthInBytes());
+    var empty = new Uint32List.view(array.buffer,
+                                    array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Uint32List);
     Expect.equals(0, empty.length);
-    var whole = new Uint32List.view(array.asByteArray());
+    var whole = new Uint32List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Uint32List);
     Expect.equals(12, whole.length);
-    var view = new Uint32List.view(array.asByteArray(), 4, 10);
+    var view = new Uint32List.view(array.buffer, 4, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Uint32List);
     Expect.equals(10, view.length);
-    Expect.equals(4, view.bytesPerElement());
-    Expect.equals(40, view.lengthInBytes());
+    Expect.equals(4, view.elementSizeInBytes);
+    Expect.equals(40, view.lengthInBytes);
     Expect.listEquals([0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF,
                        0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF],
                       view);
@@ -1610,39 +1610,39 @@
 
   static testInt64ListViewImpl(var array) {
     Expect.equals(96, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(96, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(96, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xFF;
     }
-    Expect.throws(() { new Int64List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Int64List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int64List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Int64List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int64List.view(array.asByteArray(),
-                                          array.lengthInBytes() + 1); },
+    Expect.throws(() { new Int64List.view(array.buffer,
+                                          array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int64List.view(array.asByteArray(),
+    Expect.throws(() { new Int64List.view(array.buffer,
                                           0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int64List.view(array.asByteArray(),
+    Expect.throws(() { new Int64List.view(array.buffer,
                                           array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Int64List.view(array.asByteArray(),
-                                   array.lengthInBytes());
+    var empty = new Int64List.view(array.buffer,
+                                   array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Int64List);
     Expect.equals(0, empty.length);
-    var whole = new Int64List.view(array.asByteArray());
+    var whole = new Int64List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Int64List);
     Expect.equals(12, whole.length);
-    var view = new Int64List.view(array.asByteArray(), 8, 10);
+    var view = new Int64List.view(array.buffer, 8, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Int64List);
     Expect.equals(10, view.length);
-    Expect.equals(8, view.bytesPerElement());
-    Expect.equals(80, view.lengthInBytes());
+    Expect.equals(8, view.elementSizeInBytes);
+    Expect.equals(80, view.lengthInBytes);
     Expect.listEquals([-1, -1, -1, -1, -1,
                        -1, -1, -1, -1, -1],
                       view);
@@ -1810,39 +1810,39 @@
   static testUint64ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(96, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(96, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(96, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = -1;
     }
-    Expect.throws(() { new Uint64List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Uint64List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint64List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Uint64List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint64List.view(array.asByteArray(),
-                                           array.lengthInBytes() + 1); },
+    Expect.throws(() { new Uint64List.view(array.buffer,
+                                           array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint64List.view(array.asByteArray(),
+    Expect.throws(() { new Uint64List.view(array.buffer,
                                            0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint64List.view(array.asByteArray(),
+    Expect.throws(() { new Uint64List.view(array.buffer,
                                            array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Uint64List.view(array.asByteArray(),
-                                    array.lengthInBytes());
+    var empty = new Uint64List.view(array.buffer,
+                                    array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Uint64List);
     Expect.equals(0, empty.length);
-    var whole = new Uint64List.view(array.asByteArray());
+    var whole = new Uint64List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Uint64List);
     Expect.equals(12, whole.length);
-    var view = new Uint64List.view(array.asByteArray(), 8, 10);
+    var view = new Uint64List.view(array.buffer, 8, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Uint64List);
     Expect.equals(10, view.length);
-    Expect.equals(8, view.bytesPerElement());
-    Expect.equals(80, view.lengthInBytes());
+    Expect.equals(8, view.elementSizeInBytes);
+    Expect.equals(80, view.lengthInBytes);
     Expect.listEquals([0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF,
                        0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF,
                        0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF,
@@ -1971,39 +1971,39 @@
   static testFloat32ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(12, array.length);
-    Expect.equals(4, array.bytesPerElement());
-    Expect.equals(48, array.lengthInBytes());
+    Expect.equals(4, array.elementSizeInBytes);
+    Expect.equals(48, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xBF800000;
     }
-    Expect.throws(() { new Float32List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Float32List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float32List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Float32List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float32List.view(array.asByteArray(),
-                                            array.lengthInBytes() + 1); },
+    Expect.throws(() { new Float32List.view(array.buffer,
+                                            array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float32List.view(array.asByteArray(),
-                                            0, array.lengthInBytes() + 1); },
+    Expect.throws(() { new Float32List.view(array.buffer,
+                                            0, array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float32List.view(array.asByteArray(),
-                                            array.lengthInBytes() - 1, 2); },
+    Expect.throws(() { new Float32List.view(array.buffer,
+                                            array.lengthInBytes - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Float32List.view(array.asByteArray(),
-                                     array.lengthInBytes());
+    var empty = new Float32List.view(array.buffer,
+                                     array.lengthInBytes);
     Expect.isTrue(empty is List<double>);
     Expect.isTrue(empty is Float32List);
     Expect.equals(0, empty.length);
-    var whole = new Float32List.view(array.asByteArray());
+    var whole = new Float32List.view(array.buffer);
     Expect.isTrue(whole is List<double>);
     Expect.isTrue(whole is Float32List);
     Expect.equals(12, whole.length);
-    var view = new Float32List.view(array.asByteArray(), 4, 10);
+    var view = new Float32List.view(array.buffer, 4, 10);
     Expect.isTrue(view is List<double>);
     Expect.isTrue(view is Float32List);
     Expect.equals(10, view.length);
-    Expect.equals(4, view.bytesPerElement());
-    Expect.equals(40, view.lengthInBytes());
+    Expect.equals(4, view.elementSizeInBytes);
+    Expect.equals(40, view.lengthInBytes);
     Expect.listEquals([-1.0, -1.0, -1.0, -1.0, -1.0,
                        -1.0, -1.0, -1.0, -1.0, -1.0],
                       view);
@@ -2078,39 +2078,39 @@
   static testFloat64ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(12, array.length);
-    Expect.equals(8, array.bytesPerElement());
-    Expect.equals(96, array.lengthInBytes());
+    Expect.equals(8, array.elementSizeInBytes);
+    Expect.equals(96, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xBFF0000000000000;
     }
-    Expect.throws(() { new Float64List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Float64List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float64List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Float64List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float64List.view(array.asByteArray(),
-                                            array.lengthInBytes() + 1); },
+    Expect.throws(() { new Float64List.view(array.buffer,
+                                            array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float64List.view(array.asByteArray(),
-                                            0, array.lengthInBytes() + 1); },
+    Expect.throws(() { new Float64List.view(array.buffer,
+                                            0, array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float64List.view(array.asByteArray(),
-                                            array.lengthInBytes() - 1, 2); },
+    Expect.throws(() { new Float64List.view(array.buffer,
+                                            array.lengthInBytes - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Float64List.view(array.asByteArray(),
-                                     array.lengthInBytes());
+    var empty = new Float64List.view(array.buffer,
+                                     array.lengthInBytes);
     Expect.isTrue(empty is List<double>);
     Expect.isTrue(empty is Float64List);
     Expect.equals(0, empty.length);
-    var whole = new Float64List.view(array.asByteArray());
+    var whole = new Float64List.view(array.buffer);
     Expect.isTrue(whole is List<double>);
     Expect.isTrue(whole is Float64List);
     Expect.equals(12, whole.length);
-    var view = new Float64List.view(array.asByteArray(), 8, 10);
+    var view = new Float64List.view(array.buffer, 8, 10);
     Expect.isTrue(view is List<double>);
     Expect.isTrue(view is Float64List);
     Expect.equals(10, view.length);
-    Expect.equals(8, view.bytesPerElement());
-    Expect.equals(80, view.lengthInBytes());
+    Expect.equals(8, view.elementSizeInBytes);
+    Expect.equals(80, view.lengthInBytes);
     Expect.listEquals([-1.0, -1.0, -1.0, -1.0, -1.0,
                        -1.0, -1.0, -1.0, -1.0, -1.0],
                       view);
diff --git a/runtime/tests/vm/dart/byte_array_test.dart b/runtime/tests/vm/dart/byte_array_test.dart
index 9770cad..eecd716 100644
--- a/runtime/tests/vm/dart/byte_array_test.dart
+++ b/runtime/tests/vm/dart/byte_array_test.dart
@@ -5,14 +5,14 @@
 // Library tag to be able to run in html test framework.
 library byte_array_test;
 
-import 'dart:scalarlist';
+import 'dart:typeddata';
 
 class ByteArrayTest {
   static testInt8ListImpl(Int8List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(10, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(10, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -105,8 +105,8 @@
   static testUint8ListImpl(Uint8List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(10, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(10, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -188,8 +188,8 @@
   static testUint8ClampedListImpl(Uint8ClampedList array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(10, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(10, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -267,8 +267,8 @@
   static testInt16ListImpl(Int16List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(2, array.bytesPerElement());
-    Expect.equals(20, array.lengthInBytes());
+    Expect.equals(2, array.elementSizeInBytes);
+    Expect.equals(20, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -362,8 +362,8 @@
   static testUint16ListImpl(Uint16List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(2, array.bytesPerElement());
-    Expect.equals(20, array.lengthInBytes());
+    Expect.equals(2, array.elementSizeInBytes);
+    Expect.equals(20, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -445,8 +445,8 @@
   static testInt32ListImpl(Int32List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(4, array.bytesPerElement());
-    Expect.equals(40, array.lengthInBytes());
+    Expect.equals(4, array.elementSizeInBytes);
+    Expect.equals(40, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -546,8 +546,8 @@
   static testUint32ListImpl(Uint32List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(4, array.bytesPerElement());
-    Expect.equals(40, array.lengthInBytes());
+    Expect.equals(4, array.elementSizeInBytes);
+    Expect.equals(40, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -633,8 +633,8 @@
   static testInt64ListImpl(Int64List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(8, array.bytesPerElement());
-    Expect.equals(80, array.lengthInBytes());
+    Expect.equals(8, array.elementSizeInBytes);
+    Expect.equals(80, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -735,8 +735,8 @@
   static testUint64ListImpl(Uint64List array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(10, array.length);
-    Expect.equals(8, array.bytesPerElement());
-    Expect.equals(80, array.lengthInBytes());
+    Expect.equals(8, array.elementSizeInBytes);
+    Expect.equals(80, array.lengthInBytes);
     Expect.listEquals([0, 0, 0, 0, 0,
                        0, 0, 0, 0, 0],
                       array);
@@ -821,8 +821,8 @@
   static testFloat32ListImpl(Float32List array) {
     Expect.isTrue(array is List<double>);
     Expect.equals(10, array.length);
-    Expect.equals(4, array.bytesPerElement());
-    Expect.equals(40, array.lengthInBytes());
+    Expect.equals(4, array.elementSizeInBytes);
+    Expect.equals(40, array.lengthInBytes);
     Expect.listEquals([0.0, 0.0, 0.0, 0.0, 0.0,
                        0.0, 0.0, 0.0, 0.0, 0.0],
                       array);
@@ -894,8 +894,8 @@
   static testFloat64ListImpl(Float64List array) {
     Expect.isTrue(array is List<double>);
     Expect.equals(10, array.length);
-    Expect.equals(8, array.bytesPerElement());
-    Expect.equals(80, array.lengthInBytes());
+    Expect.equals(8, array.elementSizeInBytes);
+    Expect.equals(80, array.lengthInBytes);
     Expect.listEquals([0.0, 0.0, 0.0, 0.0, 0.0,
                        0.0, 0.0, 0.0, 0.0, 0.0],
                       array);
@@ -965,9 +965,9 @@
   static testByteList() {
     var array = new Uint8List(8);
     Expect.equals(8, array.length);
-    Expect.equals(8, array.lengthInBytes());
-    var byte_array = array.asByteArray(0, array.lengthInBytes());
-    Expect.equals(8, byte_array.lengthInBytes());
+    Expect.equals(8, array.lengthInBytes);
+    var byte_array = new ByteData.view(array.buffer);
+    Expect.equals(8, byte_array.lengthInBytes);
     Expect.throws(() { byte_array.getInt8(-1); },
                   (e) { return e is RangeError; });
     Expect.throws(() { byte_array.getUint8(-1); },
@@ -1109,39 +1109,39 @@
 
   static testInt8ListViewImpl(var array) {
     Expect.equals(12, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(12, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(12, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xFF;
     }
-    Expect.throws(() { new Int8List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Int8List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int8List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Int8List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int8List.view(array.asByteArray(),
-                                         array.lengthInBytes() + 1); },
+    Expect.throws(() { new Int8List.view(array.buffer,
+                                         array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int8List.view(array.asByteArray(),
+    Expect.throws(() { new Int8List.view(array.buffer,
                                          0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int8List.view(array.asByteArray(),
+    Expect.throws(() { new Int8List.view(array.buffer,
                                          array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Int8List.view(array.asByteArray(),
-                                  array.lengthInBytes());
+    var empty = new Int8List.view(array.buffer,
+                                  array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Int8List);
     Expect.equals(0, empty.length);
-    var whole = new Int8List.view(array.asByteArray());
+    var whole = new Int8List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Int8List);
     Expect.equals(12, whole.length);
-    var view = new Int8List.view(array.asByteArray(), 1, array.length - 2);
+    var view = new Int8List.view(array.buffer, 1, array.length - 2);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Int8List);
     Expect.equals(10, view.length);
-    Expect.equals(1, view.bytesPerElement());
-    Expect.equals(10, view.lengthInBytes());
+    Expect.equals(1, view.elementSizeInBytes);
+    Expect.equals(10, view.lengthInBytes);
     Expect.listEquals([-1, -1, -1, -1, -1,
                        -1, -1, -1, -1, -1],
                       view);
@@ -1242,39 +1242,39 @@
   static testUint8ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(12, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(12, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(12, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = -1;
     }
-    Expect.throws(() { new Uint8List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Uint8List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint8List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Uint8List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint8List.view(array.asByteArray(),
-                                          array.lengthInBytes() + 1); },
+    Expect.throws(() { new Uint8List.view(array.buffer,
+                                          array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint8List.view(array.asByteArray(),
+    Expect.throws(() { new Uint8List.view(array.buffer,
                                           0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint8List.view(array.asByteArray(),
+    Expect.throws(() { new Uint8List.view(array.buffer,
                                           array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Uint8List.view(array.asByteArray(),
-                                   array.lengthInBytes());
+    var empty = new Uint8List.view(array.buffer,
+                                   array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Uint8List);
     Expect.equals(0, empty.length);
-    var whole = new Uint8List.view(array.asByteArray());
+    var whole = new Uint8List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Uint8List);
     Expect.equals(12, whole.length);
-    var view = new Uint8List.view(array.asByteArray(), 1, array.length - 2);
+    var view = new Uint8List.view(array.buffer, 1, array.length - 2);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Uint8List);
     Expect.equals(10, view.length);
-    Expect.equals(1, view.bytesPerElement());
-    Expect.equals(10, view.lengthInBytes());
+    Expect.equals(1, view.elementSizeInBytes);
+    Expect.equals(10, view.lengthInBytes);
     Expect.listEquals([0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
                        0xFF, 0xFF, 0xFF, 0xFF, 0xFF],
                       view);
@@ -1355,39 +1355,39 @@
 
   static testInt16ListViewImpl(var array) {
     Expect.equals(24, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(24, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(24, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xFF;
     }
-    Expect.throws(() { new Int16List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Int16List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int16List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Int16List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int16List.view(array.asByteArray(),
-                                          array.lengthInBytes() + 1); },
+    Expect.throws(() { new Int16List.view(array.buffer,
+                                          array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int16List.view(array.asByteArray(),
-                                           0, array.length + 1); },
+    Expect.throws(() { new Int16List.view(array.buffer,
+                                          0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int16List.view(array.asByteArray(),
-                                           array.length - 1, 2); },
+    Expect.throws(() { new Int16List.view(array.buffer,
+                                          array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Int16List.view(array.asByteArray(),
-                                   array.lengthInBytes());
+    var empty = new Int16List.view(array.buffer,
+                                   array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Int16List);
     Expect.equals(0, empty.length);
-    var whole = new Int16List.view(array.asByteArray());
+    var whole = new Int16List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Int16List);
     Expect.equals(12, whole.length);
-    var view = new Int16List.view(array.asByteArray(), 2, 10);
+    var view = new Int16List.view(array.buffer, 2, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Int16List);
     Expect.equals(10, view.length);
-    Expect.equals(2, view.bytesPerElement());
-    Expect.equals(20, view.lengthInBytes());
+    Expect.equals(2, view.elementSizeInBytes);
+    Expect.equals(20, view.lengthInBytes);
     Expect.listEquals([-1, -1, -1, -1, -1,
                        -1, -1, -1, -1, -1],
                       view);
@@ -1496,39 +1496,39 @@
   static testUint16ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(24, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(24, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(24, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = -1;
     }
-    Expect.throws(() { new Uint16List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Uint16List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint16List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Uint16List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint16List.view(array.asByteArray(),
-                                           array.lengthInBytes() + 1); },
+    Expect.throws(() { new Uint16List.view(array.buffer,
+                                           array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint16List.view(array.asByteArray(),
+    Expect.throws(() { new Uint16List.view(array.buffer,
                                            0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint16List.view(array.asByteArray(),
+    Expect.throws(() { new Uint16List.view(array.buffer,
                                            array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Uint16List.view(array.asByteArray(),
-                                    array.lengthInBytes());
+    var empty = new Uint16List.view(array.buffer,
+                                    array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Uint16List);
     Expect.equals(0, empty.length);
-    var whole = new Uint16List.view(array.asByteArray());
+    var whole = new Uint16List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Uint16List);
     Expect.equals(12, whole.length);
-    var view = new Uint16List.view(array.asByteArray(), 2, 10);
+    var view = new Uint16List.view(array.buffer, 2, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Uint16List);
     Expect.equals(10, view.length);
-    Expect.equals(2, view.bytesPerElement());
-    Expect.equals(20, view.lengthInBytes());
+    Expect.equals(2, view.elementSizeInBytes);
+    Expect.equals(20, view.lengthInBytes);
     Expect.listEquals([0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF,
                        0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF],
                       view);
@@ -1615,39 +1615,39 @@
   static testInt32ListView() {
     var array = new Uint8List(48);
     Expect.equals(48, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(48, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(48, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xFF;
     }
-    Expect.throws(() { new Int32List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Int32List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int32List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Int32List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int32List.view(array.asByteArray(),
-                                          array.lengthInBytes() + 1); },
+    Expect.throws(() { new Int32List.view(array.buffer,
+                                          array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int32List.view(array.asByteArray(),
+    Expect.throws(() { new Int32List.view(array.buffer,
                                           0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int32List.view(array.asByteArray(),
+    Expect.throws(() { new Int32List.view(array.buffer,
                                           array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Int32List.view(array.asByteArray(),
-                                   array.lengthInBytes());
+    var empty = new Int32List.view(array.buffer,
+                                   array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Int32List);
     Expect.equals(0, empty.length);
-    var whole = new Int32List.view(array.asByteArray());
+    var whole = new Int32List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Int32List);
     Expect.equals(12, whole.length);
-    var view = new Int32List.view(array.asByteArray(), 4, 10);
+    var view = new Int32List.view(array.buffer, 4, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Int32List);
     Expect.equals(10, view.length);
-    Expect.equals(4, view.bytesPerElement());
-    Expect.equals(40, view.lengthInBytes());
+    Expect.equals(4, view.elementSizeInBytes);
+    Expect.equals(40, view.lengthInBytes);
     Expect.listEquals([-1, -1, -1, -1, -1,
                        -1, -1, -1, -1, -1],
                       view);
@@ -1773,39 +1773,39 @@
   static testUint32ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(48, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(48, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(48, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = -1;
     }
-    Expect.throws(() { new Uint32List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Uint32List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint32List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Uint32List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint32List.view(array.asByteArray(),
-                                           array.lengthInBytes() + 1); },
+    Expect.throws(() { new Uint32List.view(array.buffer,
+                                           array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint32List.view(array.asByteArray(),
+    Expect.throws(() { new Uint32List.view(array.buffer,
                                            0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint32List.view(array.asByteArray(),
+    Expect.throws(() { new Uint32List.view(array.buffer,
                                            array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Uint32List.view(array.asByteArray(),
-                                    array.lengthInBytes());
+    var empty = new Uint32List.view(array.buffer,
+                                    array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Uint32List);
     Expect.equals(0, empty.length);
-    var whole = new Uint32List.view(array.asByteArray());
+    var whole = new Uint32List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Uint32List);
     Expect.equals(12, whole.length);
-    var view = new Uint32List.view(array.asByteArray(), 4, 10);
+    var view = new Uint32List.view(array.buffer, 4, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Uint32List);
     Expect.equals(10, view.length);
-    Expect.equals(4, view.bytesPerElement());
-    Expect.equals(40, view.lengthInBytes());
+    Expect.equals(4, view.elementSizeInBytes);
+    Expect.equals(40, view.lengthInBytes);
     Expect.listEquals([0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF,
                        0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF],
                       view);
@@ -1908,39 +1908,39 @@
 
   static testInt64ListViewImpl(var array) {
     Expect.equals(96, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(96, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(96, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xFF;
     }
-    Expect.throws(() { new Int64List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Int64List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int64List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Int64List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int64List.view(array.asByteArray(),
-                                          array.lengthInBytes() + 1); },
+    Expect.throws(() { new Int64List.view(array.buffer,
+                                          array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int64List.view(array.asByteArray(),
+    Expect.throws(() { new Int64List.view(array.buffer,
                                           0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Int64List.view(array.asByteArray(),
+    Expect.throws(() { new Int64List.view(array.buffer,
                                           array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Int64List.view(array.asByteArray(),
-                                   array.lengthInBytes());
+    var empty = new Int64List.view(array.buffer,
+                                   array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Int64List);
     Expect.equals(0, empty.length);
-    var whole = new Int64List.view(array.asByteArray());
+    var whole = new Int64List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Int64List);
     Expect.equals(12, whole.length);
-    var view = new Int64List.view(array.asByteArray(), 8, 10);
+    var view = new Int64List.view(array.buffer, 8, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Int64List);
     Expect.equals(10, view.length);
-    Expect.equals(8, view.bytesPerElement());
-    Expect.equals(80, view.lengthInBytes());
+    Expect.equals(8, view.elementSizeInBytes);
+    Expect.equals(80, view.lengthInBytes);
     Expect.listEquals([-1, -1, -1, -1, -1,
                        -1, -1, -1, -1, -1],
                       view);
@@ -2110,39 +2110,39 @@
   static testUint64ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(96, array.length);
-    Expect.equals(1, array.bytesPerElement());
-    Expect.equals(96, array.lengthInBytes());
+    Expect.equals(1, array.elementSizeInBytes);
+    Expect.equals(96, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = -1;
     }
-    Expect.throws(() { new Uint64List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Uint64List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint64List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Uint64List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint64List.view(array.asByteArray(),
-                                           array.lengthInBytes() + 1); },
+    Expect.throws(() { new Uint64List.view(array.buffer,
+                                           array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint64List.view(array.asByteArray(),
+    Expect.throws(() { new Uint64List.view(array.buffer,
                                            0, array.length + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Uint64List.view(array.asByteArray(),
+    Expect.throws(() { new Uint64List.view(array.buffer,
                                            array.length - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Uint64List.view(array.asByteArray(),
-                                    array.lengthInBytes());
+    var empty = new Uint64List.view(array.buffer,
+                                    array.lengthInBytes);
     Expect.isTrue(empty is List<int>);
     Expect.isTrue(empty is Uint64List);
     Expect.equals(0, empty.length);
-    var whole = new Uint64List.view(array.asByteArray());
+    var whole = new Uint64List.view(array.buffer);
     Expect.isTrue(whole is List<int>);
     Expect.isTrue(whole is Uint64List);
     Expect.equals(12, whole.length);
-    var view = new Uint64List.view(array.asByteArray(), 8, 10);
+    var view = new Uint64List.view(array.buffer, 8, 10);
     Expect.isTrue(view is List<int>);
     Expect.isTrue(view is Uint64List);
     Expect.equals(10, view.length);
-    Expect.equals(8, view.bytesPerElement());
-    Expect.equals(80, view.lengthInBytes());
+    Expect.equals(8, view.elementSizeInBytes);
+    Expect.equals(80, view.lengthInBytes);
     Expect.listEquals([0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF,
                        0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF,
                        0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF,
@@ -2273,39 +2273,39 @@
   static testFloat32ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(12, array.length);
-    Expect.equals(4, array.bytesPerElement());
-    Expect.equals(48, array.lengthInBytes());
+    Expect.equals(4, array.elementSizeInBytes);
+    Expect.equals(48, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xBF800000;
     }
-    Expect.throws(() { new Float32List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Float32List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float32List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Float32List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float32List.view(array.asByteArray(),
-                                            array.lengthInBytes() + 1); },
+    Expect.throws(() { new Float32List.view(array.buffer,
+                                            array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float32List.view(array.asByteArray(),
-                                            0, array.lengthInBytes() + 1); },
+    Expect.throws(() { new Float32List.view(array.buffer,
+                                            0, array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float32List.view(array.asByteArray(),
-                                            array.lengthInBytes() - 1, 2); },
+    Expect.throws(() { new Float32List.view(array.buffer,
+                                            array.lengthInBytes - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Float32List.view(array.asByteArray(),
-                                     array.lengthInBytes());
+    var empty = new Float32List.view(array.buffer,
+                                     array.lengthInBytes);
     Expect.isTrue(empty is List<double>);
     Expect.isTrue(empty is Float32List);
     Expect.equals(0, empty.length);
-    var whole = new Float32List.view(array.asByteArray());
+    var whole = new Float32List.view(array.buffer);
     Expect.isTrue(whole is List<double>);
     Expect.isTrue(whole is Float32List);
     Expect.equals(12, whole.length);
-    var view = new Float32List.view(array.asByteArray(), 4, 10);
+    var view = new Float32List.view(array.buffer, 4, 10);
     Expect.isTrue(view is List<double>);
     Expect.isTrue(view is Float32List);
     Expect.equals(10, view.length);
-    Expect.equals(4, view.bytesPerElement());
-    Expect.equals(40, view.lengthInBytes());
+    Expect.equals(4, view.elementSizeInBytes);
+    Expect.equals(40, view.lengthInBytes);
     Expect.listEquals([-1.0, -1.0, -1.0, -1.0, -1.0,
                        -1.0, -1.0, -1.0, -1.0, -1.0],
                       view);
@@ -2382,39 +2382,39 @@
   static testFloat64ListViewImpl(var array) {
     Expect.isTrue(array is List<int>);
     Expect.equals(12, array.length);
-    Expect.equals(8, array.bytesPerElement());
-    Expect.equals(96, array.lengthInBytes());
+    Expect.equals(8, array.elementSizeInBytes);
+    Expect.equals(96, array.lengthInBytes);
     for (int i = 0; i < array.length; ++i) {
       array[i] = 0xBFF0000000000000;
     }
-    Expect.throws(() { new Float64List.view(array.asByteArray(), -1); },
+    Expect.throws(() { new Float64List.view(array.buffer, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float64List.view(array.asByteArray(), 0, -1); },
+    Expect.throws(() { new Float64List.view(array.buffer, 0, -1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float64List.view(array.asByteArray(),
-                                            array.lengthInBytes() + 1); },
+    Expect.throws(() { new Float64List.view(array.buffer,
+                                            array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float64List.view(array.asByteArray(),
-                                            0, array.lengthInBytes() + 1); },
+    Expect.throws(() { new Float64List.view(array.buffer,
+                                            0, array.lengthInBytes + 1); },
                   (e) { return e is RangeError; });
-    Expect.throws(() { new Float64List.view(array.asByteArray(),
-                                            array.lengthInBytes() - 1, 2); },
+    Expect.throws(() { new Float64List.view(array.buffer,
+                                            array.lengthInBytes - 1, 2); },
                   (e) { return e is RangeError; });
-    var empty = new Float64List.view(array.asByteArray(),
-                                     array.lengthInBytes());
+    var empty = new Float64List.view(array.buffer,
+                                     array.lengthInBytes);
     Expect.isTrue(empty is List<double>);
     Expect.isTrue(empty is Float64List);
     Expect.equals(0, empty.length);
-    var whole = new Float64List.view(array.asByteArray());
+    var whole = new Float64List.view(array.buffer);
     Expect.isTrue(whole is List<double>);
     Expect.isTrue(whole is Float64List);
     Expect.equals(12, whole.length);
-    var view = new Float64List.view(array.asByteArray(), 8, 10);
+    var view = new Float64List.view(array.buffer, 8, 10);
     Expect.isTrue(view is List<double>);
     Expect.isTrue(view is Float64List);
     Expect.equals(10, view.length);
-    Expect.equals(8, view.bytesPerElement());
-    Expect.equals(80, view.lengthInBytes());
+    Expect.equals(8, view.elementSizeInBytes);
+    Expect.equals(80, view.lengthInBytes);
     Expect.listEquals([-1.0, -1.0, -1.0, -1.0, -1.0,
                        -1.0, -1.0, -1.0, -1.0, -1.0],
                       view);
@@ -2500,7 +2500,7 @@
     testUint64List();
     testFloat32List();
     testFloat64List();
-    testByteList();
+
     testInt8ListView();
     testUint8ListView();
     testInt16ListView();
@@ -2511,6 +2511,8 @@
     testUint64ListView();
     testFloat32ListView();
     testFloat64ListView();
+
+    testByteList();
   }
 }
 
diff --git a/runtime/tests/vm/vm.status b/runtime/tests/vm/vm.status
index a86de87..b341251 100644
--- a/runtime/tests/vm/vm.status
+++ b/runtime/tests/vm/vm.status
@@ -65,18 +65,11 @@
 # Tests needing Dart execution.
 dart/*: Skip
 
-[ $arch == simarm && $checked]
-# Tests needing type check support.
-cc/DartStaticResolve: Crash
-cc/DartDynamicResolve: Crash
-cc/FindCodeObject: Crash
-
 [ $arch == mips ]
 *: Skip
 
 [ $arch == simmips ]
 # Tests needing an assembler.
-cc/Call: Skip
 cc/CallLeafRuntimeStubCode: Skip
 cc/CallRuntimeStubCode: Skip
 cc/Dart2JSCompileAll: Skip
@@ -84,7 +77,6 @@
 cc/IcDataAccess: Skip
 cc/Jump: Skip
 cc/PatchStaticCall: Skip
-cc/Simple: Skip
 cc/UseDartApi: Skip
 # Tests needing Dart execution.
 dart/*: Skip
diff --git a/runtime/tools/gyp/find_mac_gcc_version.py b/runtime/tools/gyp/find_mac_gcc_version.py
new file mode 100755
index 0000000..0af8412
--- /dev/null
+++ b/runtime/tools/gyp/find_mac_gcc_version.py
@@ -0,0 +1,36 @@
+#!/usr/bin/env python
+# Copyright (c) 2013, 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 re
+import subprocess
+import sys
+
+def main():
+  job = subprocess.Popen(['xcodebuild', '-version'],
+                         stdout=subprocess.PIPE,
+                         stderr=subprocess.STDOUT)
+  stdout, stderr = job.communicate()
+  if job.returncode != 0:
+    print >>sys.stderr, stdout
+    print >>sys.stderr, stderr
+    raise Exception('Error %d running xcodebuild!' % job.returncode)
+  matches = re.findall('^Xcode (\d+)\.(\d+)(\.(\d+))?$', stdout, re.MULTILINE)
+  if len(matches) > 0:
+    major = int(matches[0][0])
+    minor = int(matches[0][1])
+
+    if major >= 4:
+      return 'com.apple.compilers.llvmgcc42'
+    elif major == 3 and minor >= 1:
+      return '4.2'
+    else:
+      raise Exception('Unknown XCode Version "%s"' % version_match)
+  else:
+    raise Exception('Could not parse output of xcodebuild "%s"' % stdout)
+
+if __name__ == '__main__':
+  if sys.platform != 'darwin':
+    raise Exception("This script only runs on Mac")
+  print main()
diff --git a/runtime/vm/assembler_arm.cc b/runtime/vm/assembler_arm.cc
index 023a05a..3e0fa6a 100644
--- a/runtime/vm/assembler_arm.cc
+++ b/runtime/vm/assembler_arm.cc
@@ -1262,20 +1262,24 @@
 
 
 void Assembler::LoadObject(Register rd, const Object& object) {
-  // Since objects in the VM heap are never relocated, test instead
-  // if (object.IsSmi() || object.InVMHeap()) {
-  // and modify the decoding code in CallPattern to understand movt, movw.
-  if (object.IsNull() ||
-      object.IsSmi() ||
-      (object.raw() == Bool::True().raw()) ||
-      (object.raw() == Bool::False().raw())) {
-    // This object is never relocated; do not use object pool.
+  // Smi's and VM heap objects are never relocated; do not use object pool.
+  if (object.IsSmi()) {
     LoadImmediate(rd, reinterpret_cast<int32_t>(object.raw()));
-    return;
+  } else if (object.InVMHeap()) {
+    // Make sure that class CallPattern is able to decode this load immediate.
+    const int32_t object_raw = reinterpret_cast<int32_t>(object.raw());
+    movw(rd, Utils::Low16Bits(object_raw));
+    const uint16_t value_high = Utils::High16Bits(object_raw);
+    if (value_high != 0) {
+      movt(rd, value_high);
+    }
+  } else {
+    // Make sure that class CallPattern is able to decode this load from the
+    // object pool.
+    const int32_t offset =
+        Array::data_offset() + 4*AddObject(object) - kHeapObjectTag;
+    LoadWordFromPoolOffset(rd, offset);
   }
-  const int32_t offset =
-      Array::data_offset() + 4*AddObject(object) - kHeapObjectTag;
-  LoadWordFromPoolOffset(rd, offset);
 }
 
 
@@ -1292,6 +1296,45 @@
 }
 
 
+void Assembler::LoadClassId(Register result, Register object) {
+  ASSERT(RawObject::kClassIdTagBit == 16);
+  ASSERT(RawObject::kClassIdTagSize == 16);
+  const intptr_t class_id_offset = Object::tags_offset() +
+      RawObject::kClassIdTagBit / kBitsPerByte;
+  ldrh(result, FieldAddress(object, class_id_offset));
+}
+
+
+void Assembler::LoadClassById(Register result, Register class_id) {
+  ASSERT(result != class_id);
+  ldr(result, FieldAddress(CTX, Context::isolate_offset()));
+  const intptr_t table_offset_in_isolate =
+      Isolate::class_table_offset() + ClassTable::table_offset();
+  ldr(result, Address(result, table_offset_in_isolate));
+  ldr(result, Address(result, class_id, LSL, 2));
+}
+
+
+void Assembler::LoadClass(Register result, Register object, Register scratch) {
+  ASSERT(scratch != result);
+  LoadClassId(scratch, object);
+
+  ldr(result, FieldAddress(CTX, Context::isolate_offset()));
+  const intptr_t table_offset_in_isolate =
+      Isolate::class_table_offset() + ClassTable::table_offset();
+  ldr(result, Address(result, table_offset_in_isolate));
+  ldr(result, Address(result, scratch, LSL, 2));
+}
+
+
+void Assembler::CompareClassId(Register object,
+                               intptr_t class_id,
+                               Register scratch) {
+  LoadClassId(scratch, object);
+  CompareImmediate(scratch, class_id);
+}
+
+
 void Assembler::Bind(Label* label) {
   ASSERT(!label->IsBound());
   int bound_pc = buffer_.Size();
@@ -1483,7 +1526,7 @@
     mvn(rd, shifter_op, cond);
   } else {
     movw(rd, Utils::Low16Bits(value), cond);
-    uint16_t value_high = Utils::High16Bits(value);
+    const uint16_t value_high = Utils::High16Bits(value);
     if (value_high != 0) {
       movt(rd, value_high, cond);
     }
@@ -1677,7 +1720,7 @@
       sub(rd, rn, ShifterOperand(IP), cond);
     } else {
       movw(IP, Utils::Low16Bits(value), cond);
-      uint16_t value_high = Utils::High16Bits(value);
+      const uint16_t value_high = Utils::High16Bits(value);
       if (value_high != 0) {
         movt(IP, value_high, cond);
       }
@@ -1704,7 +1747,7 @@
       subs(rd, rn, ShifterOperand(IP), cond);
     } else {
       movw(IP, Utils::Low16Bits(value), cond);
-      uint16_t value_high = Utils::High16Bits(value);
+      const uint16_t value_high = Utils::High16Bits(value);
       if (value_high != 0) {
         movt(IP, value_high, cond);
       }
@@ -1731,7 +1774,7 @@
       sbc(rd, rn, ShifterOperand(IP), cond);
     } else {
       movw(IP, Utils::Low16Bits(value), cond);
-      uint16_t value_high = Utils::High16Bits(value);
+      const uint16_t value_high = Utils::High16Bits(value);
       if (value_high != 0) {
         movt(IP, value_high, cond);
       }
@@ -1934,14 +1977,14 @@
   if (object_pool_.IsNull()) {
     // The object pool cannot be used in the vm isolate.
     ASSERT(Isolate::Current() != Dart::vm_isolate());
-    object_pool_ = GrowableObjectArray::New();
+    object_pool_ = GrowableObjectArray::New(Heap::kOld);
   }
   for (int i = 0; i < object_pool_.Length(); i++) {
     if (object_pool_.At(i) == obj.raw()) {
       return i;
     }
   }
-  object_pool_.Add(obj);
+  object_pool_.Add(obj, Heap::kOld);
   return object_pool_.Length() - 1;
 }
 
@@ -1950,7 +1993,7 @@
   if (object_pool_.IsNull()) {
     // The object pool cannot be used in the vm isolate.
     ASSERT(Isolate::Current() != Dart::vm_isolate());
-    object_pool_ = GrowableObjectArray::New();
+    object_pool_ = GrowableObjectArray::New(Heap::kOld);
   }
   const word address = label->address();
   ASSERT(Utils::IsAligned(address, 4));
@@ -1958,7 +2001,7 @@
   const Smi& smi = Smi::Handle(Smi::New(address >> kSmiTagShift));
   // Do not reuse an existing entry, since each reference may be patched
   // independently.
-  object_pool_.Add(smi);
+  object_pool_.Add(smi, Heap::kOld);
   return object_pool_.Length() - 1;
 }
 
diff --git a/runtime/vm/assembler_arm.h b/runtime/vm/assembler_arm.h
index 199b80c..64a51e9 100644
--- a/runtime/vm/assembler_arm.h
+++ b/runtime/vm/assembler_arm.h
@@ -551,11 +551,20 @@
   void LoadSImmediate(SRegister sd, float value, Condition cond = AL);
   void LoadDImmediate(DRegister dd, double value,
                       Register scratch, Condition cond = AL);
+
   void MarkExceptionHandler(Label* label);
+
   void Drop(intptr_t stack_elements);
+
   void LoadObject(Register rd, const Object& object);
   void PushObject(const Object& object);
   void CompareObject(Register rn, const Object& object);
+
+  void LoadClassId(Register result, Register object);
+  void LoadClassById(Register result, Register class_id);
+  void LoadClass(Register result, Register object, Register scratch);
+  void CompareClassId(Register object, intptr_t class_id, Register scratch);
+
   void LoadWordFromPoolOffset(Register rd, int32_t offset);
   void LoadFromOffset(LoadOperandType type,
                       Register reg,
diff --git a/runtime/vm/assembler_mips.cc b/runtime/vm/assembler_mips.cc
index 88bd937..8bc87cc 100644
--- a/runtime/vm/assembler_mips.cc
+++ b/runtime/vm/assembler_mips.cc
@@ -9,7 +9,7 @@
 
 namespace dart {
 
-DEFINE_FLAG(bool, print_stop_message, true, "Print stop message.");
+DEFINE_FLAG(bool, print_stop_message, false, "Print stop message.");
 
 
 void Assembler::InitializeMemoryWithBreakpoints(uword data, int length) {
@@ -27,11 +27,11 @@
   ASSERT(!label->IsBound());
   int bound_pc = buffer_.Size();
   while (label->IsLinked()) {
-    int32_t position = label->Position();
-    int32_t next = buffer_.Load<int32_t>(position);
-    // Reletive destination from an instruction after the branch.
-    int32_t dest = bound_pc - (position + Instr::kInstrSize);
-    int32_t encoded = Assembler::EncodeBranchOffset(dest, next);
+    const int32_t position = label->Position();
+    const int32_t next = buffer_.Load<int32_t>(position);
+    // Relative destination from an instruction after the branch.
+    const int32_t dest = bound_pc - (position + Instr::kInstrSize);
+    const int32_t encoded = Assembler::EncodeBranchOffset(dest, next);
     buffer_.Store<int32_t>(position, encoded);
     label->position_ = Assembler::DecodeBranchOffset(next);
   }
@@ -56,6 +56,72 @@
   return (((instr & kBranchOffsetMask) << 16) >> 14);
 }
 
+
+void Assembler::LoadWordFromPoolOffset(Register rd, int32_t offset) {
+  ASSERT(rd != PP);
+  if (Address::CanHoldOffset(offset)) {
+    lw(rd, Address(PP, offset));
+  } else {
+    const int16_t offset_low = Utils::Low16Bits(offset);  // Signed.
+    offset -= offset_low;
+    const uint16_t offset_high = Utils::High16Bits(offset);  // Unsigned.
+    if (offset_high != 0) {
+      lui(rd, Immediate(offset_high));
+      addu(rd, rd, PP);
+      lw(rd, Address(rd, offset_low));
+    } else {
+      lw(rd, Address(PP, offset_low));
+    }
+  }
+}
+
+
+int32_t Assembler::AddObject(const Object& obj) {
+  ASSERT(obj.IsNotTemporaryScopedHandle());
+  ASSERT(obj.IsOld());
+  if (object_pool_.IsNull()) {
+    // The object pool cannot be used in the vm isolate.
+    ASSERT(Isolate::Current() != Dart::vm_isolate());
+    object_pool_ = GrowableObjectArray::New(Heap::kOld);
+  }
+  for (int i = 0; i < object_pool_.Length(); i++) {
+    if (object_pool_.At(i) == obj.raw()) {
+      return i;
+    }
+  }
+  object_pool_.Add(obj, Heap::kOld);
+  return object_pool_.Length() - 1;
+}
+
+
+int32_t Assembler::AddExternalLabel(const ExternalLabel* label) {
+  if (object_pool_.IsNull()) {
+    // The object pool cannot be used in the vm isolate.
+    ASSERT(Isolate::Current() != Dart::vm_isolate());
+    object_pool_ = GrowableObjectArray::New(Heap::kOld);
+  }
+  const word address = label->address();
+  ASSERT(Utils::IsAligned(address, 4));
+  // The address is stored in the object array as a RawSmi.
+  const Smi& smi = Smi::Handle(Smi::New(address >> kSmiTagShift));
+  // Do not reuse an existing entry, since each reference may be patched
+  // independently.
+  object_pool_.Add(smi, Heap::kOld);
+  return object_pool_.Length() - 1;
+}
+
+
+void Assembler::Stop(const char* message) {
+  if (FLAG_print_stop_message) {
+    UNIMPLEMENTED();
+  }
+  Label stop;
+  b(&stop);
+  Emit(reinterpret_cast<int32_t>(message));
+  Bind(&stop);
+  break_(Instr::kStopMessageCode);
+}
+
 }  // namespace dart
 
 #endif  // defined TARGET_ARCH_MIPS
diff --git a/runtime/vm/assembler_mips.h b/runtime/vm/assembler_mips.h
index ed85493..81f9810 100644
--- a/runtime/vm/assembler_mips.h
+++ b/runtime/vm/assembler_mips.h
@@ -58,6 +58,10 @@
     return (base_ << kRsShift) | imm_value;
   }
 
+  static bool CanHoldOffset(int32_t offset) {
+    return Utils::IsInt(16, offset);
+  }
+
  private:
   Register base_;
   int32_t offset_;
@@ -143,9 +147,7 @@
         comments_() { }
   ~Assembler() { }
 
-  void PopRegister(Register r) {
-    UNIMPLEMENTED();
-  }
+  void PopRegister(Register r) { Pop(r); }
 
   void Bind(Label* label);
 
@@ -190,7 +192,7 @@
   }
 
   // Debugging and bringup support.
-  void Stop(const char* message) { UNIMPLEMENTED(); }
+  void Stop(const char* message);
   void Unimplemented(const char* message);
   void Untested(const char* message);
   void Unreachable(const char* message);
@@ -225,7 +227,7 @@
   // CPU instructions in alphabetical order.
   void addiu(Register rt, Register rs, const Immediate& imm) {
     ASSERT(Utils::IsInt(16, imm.value()));
-    uint16_t imm_value = static_cast<uint16_t>(imm.value());
+    const uint16_t imm_value = static_cast<uint16_t>(imm.value());
     EmitIType(ADDIU, rs, rt, imm_value);
   }
 
@@ -239,7 +241,7 @@
 
   void andi(Register rt, Register rs, const Immediate& imm) {
     ASSERT(Utils::IsUint(16, imm.value()));
-    uint16_t imm_value = static_cast<uint16_t>(imm.value());
+    const uint16_t imm_value = static_cast<uint16_t>(imm.value());
     EmitIType(ANDI, rs, rt, imm_value);
   }
 
@@ -503,15 +505,87 @@
   }
 
   // Macros in alphabetical order.
+
+  void Branch(const ExternalLabel* label) {
+    // Doesn't need to be patchable, so use the delay slot.
+    if (Utils::IsInt(16, label->address())) {
+      jr(TMP);
+      delay_slot()->addiu(TMP, ZR, Immediate(label->address()));
+    } else {
+      const uint16_t low = Utils::Low16Bits(label->address());
+      const uint16_t high = Utils::High16Bits(label->address());
+      lui(TMP, Immediate(high));
+      jr(TMP);
+      delay_slot()->ori(TMP, TMP, Immediate(low));
+    }
+  }
+
+  void BranchLink(const ExternalLabel* label) {
+    // Doesn't need to be patchable, so use the delay slot.
+    if (Utils::IsInt(16, label->address())) {
+      jalr(TMP);
+      delay_slot()->addiu(TMP, ZR, Immediate(label->address()));
+    } else {
+      const uint16_t low = Utils::Low16Bits(label->address());
+      const uint16_t high = Utils::High16Bits(label->address());
+      lui(TMP, Immediate(high));
+      jalr(TMP);
+      delay_slot()->ori(TMP, TMP, Immediate(low));
+    }
+  }
+
+  void BranchLinkPatchable(const ExternalLabel* label) {
+    const int32_t offset =
+        Array::data_offset() + 4*AddExternalLabel(label) - kHeapObjectTag;
+    LoadWordFromPoolOffset(TMP, offset);
+    jalr(TMP);
+  }
+
+  void BranchPatchable(const ExternalLabel* label) {
+    LoadImmediate(TMP, label->address());
+    jr(TMP);
+  }
+
+  void Drop(intptr_t stack_elements) {
+    ASSERT(stack_elements >= 0);
+    if (stack_elements > 0) {
+      addiu(SP, SP, Immediate(stack_elements * kWordSize));
+    }
+  }
+
   void LoadImmediate(Register rd, int32_t value) {
     if (Utils::IsInt(16, value)) {
       addiu(rd, ZR, Immediate(value));
     } else {
-      lui(rd, Immediate((value >> 16) & 0xffff));
-      ori(rd, rd, Immediate(value & 0xffff));
+      const uint16_t low = Utils::Low16Bits(value);
+      const uint16_t high = Utils::High16Bits(value);
+      lui(rd, Immediate(high));
+      ori(rd, rd, Immediate(low));
     }
   }
 
+  void Push(Register rt) {
+    addiu(SP, SP, Immediate(-kWordSize));
+    sw(rt, Address(SP));
+  }
+
+  void Pop(Register rt) {
+    lw(rt, Address(SP));
+    addiu(SP, SP, Immediate(kWordSize));
+  }
+
+  void Ret() {
+    jr(RA);
+  }
+
+  void LoadWordFromPoolOffset(Register rd, int32_t offset);
+  void LoadObject(Register rd, const Object& object);
+  void PushObject(const Object& object);
+
+  // Sets register rd to zero if the object is equal to register rn,
+  // set to non-zero otherwise.
+  void CompareObject(Register rd, Register rn, const Object& object);
+
  private:
   AssemblerBuffer buffer_;
   GrowableObjectArray& object_pool_;  // Objects and patchable jump targets.
@@ -520,6 +594,9 @@
   bool delay_slot_available_;
   bool in_delay_slot_;
 
+  int32_t AddObject(const Object& obj);
+  int32_t AddExternalLabel(const ExternalLabel* label);
+
   class CodeComment : public ZoneAllocated {
    public:
     CodeComment(intptr_t pc_offset, const String& comment)
@@ -595,12 +672,13 @@
 
   void EmitBranch(Opcode b, Register rs, Register rt, Label* label) {
     if (label->IsBound()) {
-      // Reletive destination from an instruction after the branch.
-      int32_t dest = label->Position() - (buffer_.Size() + Instr::kInstrSize);
-      uint16_t dest_off = EncodeBranchOffset(dest, 0);
+      // Relative destination from an instruction after the branch.
+      const int32_t dest =
+          label->Position() - (buffer_.Size() + Instr::kInstrSize);
+      const uint16_t dest_off = EncodeBranchOffset(dest, 0);
       EmitIType(b, rs, rt, dest_off);
     } else {
-      int position = buffer_.Size();
+      const int position = buffer_.Size();
       EmitIType(b, rs, rt, label->position_);
       label->LinkTo(position);
     }
@@ -608,12 +686,13 @@
 
   void EmitRegImmBranch(RtRegImm b, Register rs, Label* label) {
     if (label->IsBound()) {
-      // Reletive destination from an instruction after the branch.
-      int32_t dest = label->Position() - (buffer_.Size() + Instr::kInstrSize);
-      uint16_t dest_off = EncodeBranchOffset(dest, 0);
+      // Relative destination from an instruction after the branch.
+      const int32_t dest =
+          label->Position() - (buffer_.Size() + Instr::kInstrSize);
+      const uint16_t dest_off = EncodeBranchOffset(dest, 0);
       EmitRegImmType(REGIMM, rs, b, dest_off);
     } else {
-      int position = buffer_.Size();
+      const int position = buffer_.Size();
       EmitRegImmType(REGIMM, rs, b, label->position_);
       label->LinkTo(position);
     }
diff --git a/runtime/vm/assembler_x64.cc b/runtime/vm/assembler_x64.cc
index 49acf4a..c8e2e0b 100644
--- a/runtime/vm/assembler_x64.cc
+++ b/runtime/vm/assembler_x64.cc
@@ -365,7 +365,16 @@
 }
 
 
-void Assembler::movsxl(Register dst, const Address& src) {
+void Assembler::movsxd(Register dst, Register src) {
+  AssemblerBuffer::EnsureCapacity ensured(&buffer_);
+  Operand operand(src);
+  EmitOperandREX(dst, operand, REX_W);
+  EmitUint8(0x63);
+  EmitOperand(dst & 7, operand);
+}
+
+
+void Assembler::movsxd(Register dst, const Address& src) {
   AssemblerBuffer::EnsureCapacity ensured(&buffer_);
   EmitOperandREX(dst, src, REX_W);
   EmitUint8(0x63);
diff --git a/runtime/vm/assembler_x64.h b/runtime/vm/assembler_x64.h
index d14c02d..6f049bb 100644
--- a/runtime/vm/assembler_x64.h
+++ b/runtime/vm/assembler_x64.h
@@ -365,7 +365,8 @@
   void movq(const Address& dst, Register src);
   void movq(const Address& dst, const Immediate& imm);
 
-  void movsxl(Register dst, const Address& src);
+  void movsxd(Register dst, Register src);
+  void movsxd(Register dst, const Address& src);
 
   void leaq(Register dst, const Address& src);
 
diff --git a/runtime/vm/assembler_x64_test.cc b/runtime/vm/assembler_x64_test.cc
index 1287571..2d29d9d 100644
--- a/runtime/vm/assembler_x64_test.cc
+++ b/runtime/vm/assembler_x64_test.cc
@@ -515,6 +515,22 @@
 }
 
 
+ASSEMBLER_TEST_GENERATE(MoveExtend32, assembler) {
+  __ movq(RDX, Immediate(0xffffffff));
+  __ movsxd(RDX, RDX);
+  __ movq(RAX, Immediate(0x7fffffff));
+  __ movsxd(RAX, RAX);
+  __ addq(RAX, RDX);
+  __ ret();
+}
+
+
+ASSEMBLER_TEST_RUN(MoveExtend32, test) {
+  typedef intptr_t (*MoveExtend)();
+  EXPECT_EQ(0x7ffffffe, reinterpret_cast<MoveExtend>(test->entry())());
+}
+
+
 ASSEMBLER_TEST_GENERATE(MoveExtendMemory, assembler) {
   __ movq(RDX, Immediate(0x123456781234ffff));
 
@@ -537,6 +553,24 @@
 }
 
 
+ASSEMBLER_TEST_GENERATE(MoveExtend32Memory, assembler) {
+  __ pushq(Immediate(0xffffffff));
+  __ pushq(Immediate(0x7fffffff));
+  __ movsxd(RDX, Address(RSP, kWordSize));
+  __ movsxd(RAX, Address(RSP, 0));
+  __ addq(RSP, Immediate(kWordSize * 2));
+
+  __ addq(RAX, RDX);
+  __ ret();
+}
+
+
+ASSEMBLER_TEST_RUN(MoveExtend32Memory, test) {
+  typedef intptr_t (*MoveExtend)();
+  EXPECT_EQ(0x7ffffffe, reinterpret_cast<MoveExtend>(test->entry())());
+}
+
+
 ASSEMBLER_TEST_GENERATE(MoveWord, assembler) {
   __ xorq(RAX, RAX);
   __ pushq(Immediate(0));
diff --git a/runtime/vm/benchmark_test.cc b/runtime/vm/benchmark_test.cc
index 9347fca..84c8c88 100644
--- a/runtime/vm/benchmark_test.cc
+++ b/runtime/vm/benchmark_test.cc
@@ -406,7 +406,7 @@
       "import 'dart:math';\n"
       "import 'dart:isolate';\n"
       "import 'dart:mirrors';\n"
-      "import 'dart:scalarlist';\n"
+      "import 'dart:typeddata';\n"
       "\n";
 
   // Start an Isolate, load a script and create a full snapshot.
@@ -432,7 +432,7 @@
       "import 'dart:math';\n"
       "import 'dart:isolate';\n"
       "import 'dart:mirrors';\n"
-      "import 'dart:scalarlist';\n"
+      "import 'dart:typeddata';\n"
       "import 'dart:uri';\n"
       "import 'dart:utf';\n"
       "import 'dart:json';\n"
diff --git a/runtime/vm/bootstrap_natives.h b/runtime/vm/bootstrap_natives.h
index 4c4ef11..970d967 100644
--- a/runtime/vm/bootstrap_natives.h
+++ b/runtime/vm/bootstrap_natives.h
@@ -112,6 +112,142 @@
   V(Stacktrace_setupFullStacktrace, 1)                                         \
   V(Stopwatch_now, 0)                                                          \
   V(Stopwatch_frequency, 0)                                                    \
+  V(ByteArray_getLength, 1)                                                    \
+  V(ByteArray_getInt8, 2)                                                      \
+  V(ByteArray_setInt8, 3)                                                      \
+  V(ByteArray_getUint8, 2)                                                     \
+  V(ByteArray_setUint8, 3)                                                     \
+  V(ByteArray_getInt16, 2)                                                     \
+  V(ByteArray_setInt16, 3)                                                     \
+  V(ByteArray_getUint16, 2)                                                    \
+  V(ByteArray_setUint16, 3)                                                    \
+  V(ByteArray_getInt32, 2)                                                     \
+  V(ByteArray_setInt32, 3)                                                     \
+  V(ByteArray_getUint32, 2)                                                    \
+  V(ByteArray_setUint32, 3)                                                    \
+  V(ByteArray_getInt64, 2)                                                     \
+  V(ByteArray_setInt64, 3)                                                     \
+  V(ByteArray_getUint64, 2)                                                    \
+  V(ByteArray_setUint64, 3)                                                    \
+  V(ByteArray_getFloat32, 2)                                                   \
+  V(ByteArray_setFloat32, 3)                                                   \
+  V(ByteArray_getFloat64, 2)                                                   \
+  V(ByteArray_setFloat64, 3)                                                   \
+  V(ByteArray_setRange, 5)                                                     \
+  V(Int8Array_new, 1)                                                          \
+  V(Int8List_newTransferable, 1)                                               \
+  V(Int8Array_getIndexed, 2)                                                   \
+  V(Int8Array_setIndexed, 3)                                                   \
+  V(Uint8Array_new, 1)                                                         \
+  V(Uint8List_newTransferable, 1)                                              \
+  V(Uint8Array_getIndexed, 2)                                                  \
+  V(Uint8Array_setIndexed, 3)                                                  \
+  V(Uint8ClampedArray_new, 1)                                                  \
+  V(Uint8ClampedList_newTransferable, 1)                                       \
+  V(Uint8ClampedArray_getIndexed, 2)                                           \
+  V(Uint8ClampedArray_setIndexed, 3)                                           \
+  V(Int16Array_new, 1)                                                         \
+  V(Int16List_newTransferable, 1)                                              \
+  V(Int16Array_getIndexed, 2)                                                  \
+  V(Int16Array_setIndexed, 3)                                                  \
+  V(Uint16Array_new, 1)                                                        \
+  V(Uint16List_newTransferable, 1)                                             \
+  V(Uint16Array_getIndexed, 2)                                                 \
+  V(Uint16Array_setIndexed, 3)                                                 \
+  V(Int32Array_new, 1)                                                         \
+  V(Int32List_newTransferable, 1)                                              \
+  V(Int32Array_getIndexed, 2)                                                  \
+  V(Int32Array_setIndexed, 3)                                                  \
+  V(Uint32Array_new, 1)                                                        \
+  V(Uint32List_newTransferable, 1)                                             \
+  V(Uint32Array_getIndexed, 2)                                                 \
+  V(Uint32Array_setIndexed, 3)                                                 \
+  V(Int64Array_new, 1)                                                         \
+  V(Int64List_newTransferable, 1)                                              \
+  V(Int64Array_getIndexed, 2)                                                  \
+  V(Int64Array_setIndexed, 3)                                                  \
+  V(Uint64Array_new, 1)                                                        \
+  V(Uint64List_newTransferable, 1)                                             \
+  V(Uint64Array_getIndexed, 2)                                                 \
+  V(Uint64Array_setIndexed, 3)                                                 \
+  V(Float32Array_new, 1)                                                       \
+  V(Float32List_newTransferable, 1)                                            \
+  V(Float32Array_getIndexed, 2)                                                \
+  V(Float32Array_setIndexed, 3)                                                \
+  V(Float64Array_new, 1)                                                       \
+  V(Float64List_newTransferable, 1)                                            \
+  V(Float64Array_getIndexed, 2)                                                \
+  V(Float64Array_setIndexed, 3)                                                \
+  V(ExternalInt8Array_getIndexed, 2)                                           \
+  V(ExternalInt8Array_setIndexed, 3)                                           \
+  V(ExternalUint8Array_getIndexed, 2)                                          \
+  V(ExternalUint8Array_setIndexed, 3)                                          \
+  V(ExternalUint8ClampedArray_getIndexed, 2)                                   \
+  V(ExternalUint8ClampedArray_setIndexed, 3)                                   \
+  V(ExternalInt16Array_getIndexed, 2)                                          \
+  V(ExternalInt16Array_setIndexed, 3)                                          \
+  V(ExternalUint16Array_getIndexed, 2)                                         \
+  V(ExternalUint16Array_setIndexed, 3)                                         \
+  V(ExternalInt32Array_getIndexed, 2)                                          \
+  V(ExternalInt32Array_setIndexed, 3)                                          \
+  V(ExternalUint32Array_getIndexed, 2)                                         \
+  V(ExternalUint32Array_setIndexed, 3)                                         \
+  V(ExternalInt64Array_getIndexed, 2)                                          \
+  V(ExternalInt64Array_setIndexed, 3)                                          \
+  V(ExternalUint64Array_getIndexed, 2)                                         \
+  V(ExternalUint64Array_setIndexed, 3)                                         \
+  V(ExternalFloat32Array_getIndexed, 2)                                        \
+  V(ExternalFloat32Array_setIndexed, 3)                                        \
+  V(ExternalFloat64Array_getIndexed, 2)                                        \
+  V(ExternalFloat64Array_setIndexed, 3)                                        \
+  V(TypedData_Int8Array_new, 1)                                                \
+  V(TypedData_Uint8Array_new, 1)                                               \
+  V(TypedData_Uint8ClampedArray_new, 1)                                        \
+  V(TypedData_Int16Array_new, 1)                                               \
+  V(TypedData_Uint16Array_new, 1)                                              \
+  V(TypedData_Int32Array_new, 1)                                               \
+  V(TypedData_Uint32Array_new, 1)                                              \
+  V(TypedData_Int64Array_new, 1)                                               \
+  V(TypedData_Uint64Array_new, 1)                                              \
+  V(TypedData_Float32Array_new, 1)                                             \
+  V(TypedData_Float64Array_new, 1)                                             \
+  V(TypedData_Float32x4Array_new, 1)                                           \
+  V(ExternalTypedData_Int8Array_new, 1)                                        \
+  V(ExternalTypedData_Uint8Array_new, 1)                                       \
+  V(ExternalTypedData_Uint8ClampedArray_new, 1)                                \
+  V(ExternalTypedData_Int16Array_new, 1)                                       \
+  V(ExternalTypedData_Uint16Array_new, 1)                                      \
+  V(ExternalTypedData_Int32Array_new, 1)                                       \
+  V(ExternalTypedData_Uint32Array_new, 1)                                      \
+  V(ExternalTypedData_Int64Array_new, 1)                                       \
+  V(ExternalTypedData_Uint64Array_new, 1)                                      \
+  V(ExternalTypedData_Float32Array_new, 1)                                     \
+  V(ExternalTypedData_Float64Array_new, 1)                                     \
+  V(ExternalTypedData_Float32x4Array_new, 1)                                   \
+  V(TypedData_length, 1)                                                       \
+  V(TypedData_setRange, 5)                                                     \
+  V(TypedData_GetInt8, 2)                                                      \
+  V(TypedData_SetInt8, 3)                                                      \
+  V(TypedData_GetUint8, 2)                                                     \
+  V(TypedData_SetUint8, 3)                                                     \
+  V(TypedData_GetInt16, 2)                                                     \
+  V(TypedData_SetInt16, 3)                                                     \
+  V(TypedData_GetUint16, 2)                                                    \
+  V(TypedData_SetUint16, 3)                                                    \
+  V(TypedData_GetInt32, 2)                                                     \
+  V(TypedData_SetInt32, 3)                                                     \
+  V(TypedData_GetUint32, 2)                                                    \
+  V(TypedData_SetUint32, 3)                                                    \
+  V(TypedData_GetInt64, 2)                                                     \
+  V(TypedData_SetInt64, 3)                                                     \
+  V(TypedData_GetUint64, 2)                                                    \
+  V(TypedData_SetUint64, 3)                                                    \
+  V(TypedData_GetFloat32, 2)                                                   \
+  V(TypedData_SetFloat32, 3)                                                   \
+  V(TypedData_GetFloat64, 2)                                                   \
+  V(TypedData_SetFloat64, 3)                                                   \
+  V(TypedData_GetFloat32x4, 2)                                                 \
+  V(TypedData_SetFloat32x4, 3)                                                 \
   V(Float32x4_fromDoubles, 5)                                                  \
   V(Float32x4_zero, 1)                                                         \
   V(Float32x4_add, 2)                                                          \
@@ -169,146 +305,6 @@
   V(Uint32x4_setFlagW, 2)                                                      \
   V(Uint32x4_select, 3)                                                        \
   V(Uint32x4_toFloat32x4, 1)                                                   \
-  V(ByteArray_getLength, 1)                                                    \
-  V(ByteArray_getInt8, 2)                                                      \
-  V(ByteArray_setInt8, 3)                                                      \
-  V(ByteArray_getUint8, 2)                                                     \
-  V(ByteArray_setUint8, 3)                                                     \
-  V(ByteArray_getInt16, 2)                                                     \
-  V(ByteArray_setInt16, 3)                                                     \
-  V(ByteArray_getUint16, 2)                                                    \
-  V(ByteArray_setUint16, 3)                                                    \
-  V(ByteArray_getInt32, 2)                                                     \
-  V(ByteArray_setInt32, 3)                                                     \
-  V(ByteArray_getUint32, 2)                                                    \
-  V(ByteArray_setUint32, 3)                                                    \
-  V(ByteArray_getInt64, 2)                                                     \
-  V(ByteArray_setInt64, 3)                                                     \
-  V(ByteArray_getUint64, 2)                                                    \
-  V(ByteArray_setUint64, 3)                                                    \
-  V(ByteArray_getFloat32x4, 2)                                                 \
-  V(ByteArray_setFloat32x4, 3)                                                 \
-  V(ByteArray_getFloat32, 2)                                                   \
-  V(ByteArray_setFloat32, 3)                                                   \
-  V(ByteArray_getFloat64, 2)                                                   \
-  V(ByteArray_setFloat64, 3)                                                   \
-  V(ByteArray_setRange, 5)                                                     \
-  V(Int8Array_new, 1)                                                          \
-  V(Int8List_newTransferable, 1)                                               \
-  V(Int8Array_getIndexed, 2)                                                   \
-  V(Int8Array_setIndexed, 3)                                                   \
-  V(Uint8Array_new, 1)                                                         \
-  V(Uint8List_newTransferable, 1)                                              \
-  V(Uint8Array_getIndexed, 2)                                                  \
-  V(Uint8Array_setIndexed, 3)                                                  \
-  V(Uint8ClampedArray_new, 1)                                                  \
-  V(Uint8ClampedList_newTransferable, 1)                                       \
-  V(Uint8ClampedArray_getIndexed, 2)                                           \
-  V(Uint8ClampedArray_setIndexed, 3)                                           \
-  V(Int16Array_new, 1)                                                         \
-  V(Int16List_newTransferable, 1)                                              \
-  V(Int16Array_getIndexed, 2)                                                  \
-  V(Int16Array_setIndexed, 3)                                                  \
-  V(Uint16Array_new, 1)                                                        \
-  V(Uint16List_newTransferable, 1)                                             \
-  V(Uint16Array_getIndexed, 2)                                                 \
-  V(Uint16Array_setIndexed, 3)                                                 \
-  V(Int32Array_new, 1)                                                         \
-  V(Int32List_newTransferable, 1)                                              \
-  V(Int32Array_getIndexed, 2)                                                  \
-  V(Int32Array_setIndexed, 3)                                                  \
-  V(Uint32Array_new, 1)                                                        \
-  V(Uint32List_newTransferable, 1)                                             \
-  V(Uint32Array_getIndexed, 2)                                                 \
-  V(Uint32Array_setIndexed, 3)                                                 \
-  V(Int64Array_new, 1)                                                         \
-  V(Int64List_newTransferable, 1)                                              \
-  V(Int64Array_getIndexed, 2)                                                  \
-  V(Int64Array_setIndexed, 3)                                                  \
-  V(Uint64Array_new, 1)                                                        \
-  V(Uint64List_newTransferable, 1)                                             \
-  V(Uint64Array_getIndexed, 2)                                                 \
-  V(Uint64Array_setIndexed, 3)                                                 \
-  V(Float32x4Array_new, 1)                                                     \
-  V(Float32x4List_newTransferable, 1)                                          \
-  V(Float32x4Array_getIndexed, 2)                                              \
-  V(Float32x4Array_setIndexed, 3)                                              \
-  V(Float32Array_new, 1)                                                       \
-  V(Float32List_newTransferable, 1)                                            \
-  V(Float32Array_getIndexed, 2)                                                \
-  V(Float32Array_setIndexed, 3)                                                \
-  V(Float64Array_new, 1)                                                       \
-  V(Float64List_newTransferable, 1)                                            \
-  V(Float64Array_getIndexed, 2)                                                \
-  V(Float64Array_setIndexed, 3)                                                \
-  V(ExternalInt8Array_getIndexed, 2)                                           \
-  V(ExternalInt8Array_setIndexed, 3)                                           \
-  V(ExternalUint8Array_getIndexed, 2)                                          \
-  V(ExternalUint8Array_setIndexed, 3)                                          \
-  V(ExternalUint8ClampedArray_getIndexed, 2)                                   \
-  V(ExternalUint8ClampedArray_setIndexed, 3)                                   \
-  V(ExternalInt16Array_getIndexed, 2)                                          \
-  V(ExternalInt16Array_setIndexed, 3)                                          \
-  V(ExternalUint16Array_getIndexed, 2)                                         \
-  V(ExternalUint16Array_setIndexed, 3)                                         \
-  V(ExternalInt32Array_getIndexed, 2)                                          \
-  V(ExternalInt32Array_setIndexed, 3)                                          \
-  V(ExternalUint32Array_getIndexed, 2)                                         \
-  V(ExternalUint32Array_setIndexed, 3)                                         \
-  V(ExternalInt64Array_getIndexed, 2)                                          \
-  V(ExternalInt64Array_setIndexed, 3)                                          \
-  V(ExternalUint64Array_getIndexed, 2)                                         \
-  V(ExternalUint64Array_setIndexed, 3)                                         \
-  V(ExternalFloat32x4Array_getIndexed, 2)                                      \
-  V(ExternalFloat32x4Array_setIndexed, 3)                                      \
-  V(ExternalFloat32Array_getIndexed, 2)                                        \
-  V(ExternalFloat32Array_setIndexed, 3)                                        \
-  V(ExternalFloat64Array_getIndexed, 2)                                        \
-  V(ExternalFloat64Array_setIndexed, 3)                                        \
-  V(TypedData_Int8Array_new, 1)                                                \
-  V(TypedData_Uint8Array_new, 1)                                               \
-  V(TypedData_Uint8ClampedArray_new, 1)                                        \
-  V(TypedData_Int16Array_new, 1)                                               \
-  V(TypedData_Uint16Array_new, 1)                                              \
-  V(TypedData_Int32Array_new, 1)                                               \
-  V(TypedData_Uint32Array_new, 1)                                              \
-  V(TypedData_Int64Array_new, 1)                                               \
-  V(TypedData_Uint64Array_new, 1)                                              \
-  V(TypedData_Float32Array_new, 1)                                             \
-  V(TypedData_Float64Array_new, 1)                                             \
-  V(ExternalTypedData_Int8Array_new, 1)                                        \
-  V(ExternalTypedData_Uint8Array_new, 1)                                       \
-  V(ExternalTypedData_Uint8ClampedArray_new, 1)                                \
-  V(ExternalTypedData_Int16Array_new, 1)                                       \
-  V(ExternalTypedData_Uint16Array_new, 1)                                      \
-  V(ExternalTypedData_Int32Array_new, 1)                                       \
-  V(ExternalTypedData_Uint32Array_new, 1)                                      \
-  V(ExternalTypedData_Int64Array_new, 1)                                       \
-  V(ExternalTypedData_Uint64Array_new, 1)                                      \
-  V(ExternalTypedData_Float32Array_new, 1)                                     \
-  V(ExternalTypedData_Float64Array_new, 1)                                     \
-  V(TypedData_length, 1)                                                       \
-  V(TypedData_setRange, 5)                                                     \
-  V(TypedData_GetInt8, 2)                                                      \
-  V(TypedData_SetInt8, 3)                                                      \
-  V(TypedData_GetUint8, 2)                                                     \
-  V(TypedData_SetUint8, 3)                                                     \
-  V(TypedData_GetInt16, 2)                                                     \
-  V(TypedData_SetInt16, 3)                                                     \
-  V(TypedData_GetUint16, 2)                                                    \
-  V(TypedData_SetUint16, 3)                                                    \
-  V(TypedData_GetInt32, 2)                                                     \
-  V(TypedData_SetInt32, 3)                                                     \
-  V(TypedData_GetUint32, 2)                                                    \
-  V(TypedData_SetUint32, 3)                                                    \
-  V(TypedData_GetInt64, 2)                                                     \
-  V(TypedData_SetInt64, 3)                                                     \
-  V(TypedData_GetUint64, 2)                                                    \
-  V(TypedData_SetUint64, 3)                                                    \
-  V(TypedData_GetFloat32, 2)                                                   \
-  V(TypedData_SetFloat32, 3)                                                   \
-  V(TypedData_GetFloat64, 2)                                                   \
-  V(TypedData_SetFloat64, 3)                                                   \
   V(isolate_getPortInternal, 0)                                                \
   V(isolate_spawnFunction, 2)                                                  \
   V(isolate_spawnUri, 1)                                                       \
diff --git a/runtime/vm/code_patcher_arm_test.cc b/runtime/vm/code_patcher_arm_test.cc
index 5ffdac0..6fbd1a3 100644
--- a/runtime/vm/code_patcher_arm_test.cc
+++ b/runtime/vm/code_patcher_arm_test.cc
@@ -61,8 +61,8 @@
   const Array& arg_descriptor =
       Array::ZoneHandle(ArgumentsDescriptor::New(1, Array::Handle()));
 
-  __ LoadObject(R5, ic_data);
   __ LoadObject(R4, arg_descriptor);
+  __ LoadObject(R5, ic_data);
   ExternalLabel target_label(
       "InlineCache", StubCode::OneArgCheckInlineCacheEntryPoint());
   __ BranchLinkPatchable(&target_label);
diff --git a/runtime/vm/constants_ia32.h b/runtime/vm/constants_ia32.h
index 92a5bb7..937ff99 100644
--- a/runtime/vm/constants_ia32.h
+++ b/runtime/vm/constants_ia32.h
@@ -84,6 +84,7 @@
   TIMES_2 = 1,
   TIMES_4 = 2,
   TIMES_8 = 3,
+  TIMES_16 = 4,
   TIMES_HALF_WORD_SIZE = kWordSizeLog2 - 1
 };
 
diff --git a/runtime/vm/constants_mips.h b/runtime/vm/constants_mips.h
index 95a0799..db01e25 100644
--- a/runtime/vm/constants_mips.h
+++ b/runtime/vm/constants_mips.h
@@ -172,7 +172,7 @@
   kImmBits = 16,
   kInstrShift = 0,
   kInstrBits = 26,
-  kBreakCodeShift = 5,
+  kBreakCodeShift = 6,
   kBreakCodeBits = 20,
 
   kBranchOffsetMask = 0x0000ffff,
@@ -309,6 +309,7 @@
   static const int32_t kBreakPointInstruction =
       (SPECIAL << kOpcodeShift) | (BREAK << kFunctionShift);
   static const int32_t kNopInstruction = 0;
+  static const int32_t kStopMessageCode = 1;
 
   // Get the raw instruction bits.
   inline int32_t InstructionBits() const {
diff --git a/runtime/vm/constants_x64.h b/runtime/vm/constants_x64.h
index 2cbb7e7..a343543 100644
--- a/runtime/vm/constants_x64.h
+++ b/runtime/vm/constants_x64.h
@@ -108,6 +108,7 @@
   TIMES_2 = 1,
   TIMES_4 = 2,
   TIMES_8 = 3,
+  TIMES_16 = 4,
   TIMES_HALF_WORD_SIZE = kWordSizeLog2 - 1
 };
 
diff --git a/runtime/vm/dart_api_impl.cc b/runtime/vm/dart_api_impl.cc
index 2333523..414601b 100644
--- a/runtime/vm/dart_api_impl.cc
+++ b/runtime/vm/dart_api_impl.cc
@@ -2329,47 +2329,61 @@
 static Dart_TypedData_Type GetType(intptr_t class_id) {
   Dart_TypedData_Type type;
   switch (class_id) {
+    case kByteDataViewCid :
+      type = kByteData;
+      break;
     case kTypedDataInt8ArrayCid :
+    case kTypedDataInt8ArrayViewCid :
     case kExternalTypedDataInt8ArrayCid :
       type = kInt8;
       break;
     case kTypedDataUint8ArrayCid :
+    case kTypedDataUint8ArrayViewCid :
     case kExternalTypedDataUint8ArrayCid :
       type = kUint8;
       break;
     case kTypedDataUint8ClampedArrayCid :
+    case kTypedDataUint8ClampedArrayViewCid :
     case kExternalTypedDataUint8ClampedArrayCid :
       type = kUint8Clamped;
       break;
     case kTypedDataInt16ArrayCid :
+    case kTypedDataInt16ArrayViewCid :
     case kExternalTypedDataInt16ArrayCid :
       type = kInt16;
       break;
     case kTypedDataUint16ArrayCid :
+    case kTypedDataUint16ArrayViewCid :
     case kExternalTypedDataUint16ArrayCid :
       type = kUint16;
       break;
     case kTypedDataInt32ArrayCid :
+    case kTypedDataInt32ArrayViewCid :
     case kExternalTypedDataInt32ArrayCid :
       type = kInt32;
       break;
     case kTypedDataUint32ArrayCid :
+    case kTypedDataUint32ArrayViewCid :
     case kExternalTypedDataUint32ArrayCid :
       type = kUint32;
       break;
     case kTypedDataInt64ArrayCid :
+    case kTypedDataInt64ArrayViewCid :
     case kExternalTypedDataInt64ArrayCid :
       type = kInt64;
       break;
     case kTypedDataUint64ArrayCid :
+    case kTypedDataUint64ArrayViewCid :
     case kExternalTypedDataUint64ArrayCid :
       type = kUint64;
       break;
     case kTypedDataFloat32ArrayCid :
+    case kTypedDataFloat32ArrayViewCid :
     case kExternalTypedDataFloat32ArrayCid :
       type = kFloat32;
       break;
     case kTypedDataFloat64ArrayCid :
+    case kTypedDataFloat64ArrayViewCid :
     case kExternalTypedDataFloat64ArrayCid :
       type = kFloat64;
       break;
@@ -2383,18 +2397,10 @@
 
 DART_EXPORT Dart_TypedData_Type Dart_GetTypeOfTypedData(Dart_Handle object) {
   intptr_t class_id = Api::ClassId(object);
-  if (RawObject::IsTypedDataClassId(class_id)) {
+  if (RawObject::IsTypedDataClassId(class_id) ||
+      RawObject::IsTypedDataViewClassId(class_id)) {
     return GetType(class_id);
   }
-  Isolate* isolate = Isolate::Current();
-  const Library& lib =
-      Library::Handle(isolate->object_store()->typeddata_library());
-  const Class& cls =
-      Class::Handle(isolate,
-                    lib.LookupClassAllowPrivate(Symbols::_ByteDataView()));
-  if (isolate->class_table()->At(class_id) == cls.raw()) {
-    return kByteData;
-  }
   return kInvalid;
 }
 
@@ -2402,18 +2408,10 @@
 DART_EXPORT Dart_TypedData_Type Dart_GetTypeOfExternalTypedData(
     Dart_Handle object) {
   intptr_t class_id = Api::ClassId(object);
-  if (RawObject::IsExternalTypedDataClassId(class_id)) {
+  if (RawObject::IsExternalTypedDataClassId(class_id) ||
+      RawObject::IsTypedDataViewClassId(class_id)) {
     return GetType(class_id);
   }
-  Isolate* isolate = Isolate::Current();
-  const Library& lib =
-      Library::Handle(isolate->object_store()->typeddata_library());
-  const Class& cls =
-      Class::Handle(isolate,
-                    lib.LookupClassAllowPrivate(Symbols::_ByteDataView()));
-  if (isolate->class_table()->At(class_id) == cls.raw()) {
-    return kByteData;
-  }
   return kInvalid;
 }
 
@@ -2675,6 +2673,7 @@
   DARTSCOPE(isolate);
   intptr_t class_id = Api::ClassId(object);
   if (!RawObject::IsExternalTypedDataClassId(class_id) &&
+      !RawObject::IsTypedDataViewClassId(class_id) &&
       !RawObject::IsTypedDataClassId(class_id)) {
     RETURN_TYPE_ERROR(isolate, object, 'TypedData');
   }
@@ -2695,15 +2694,33 @@
         Api::UnwrapExternalTypedDataHandle(isolate, object);
     ASSERT(!obj.IsNull());
     *len = obj.Length();
-    *data = reinterpret_cast<void*>(obj.DataAddr(0));
-  } else {
+    *data = obj.DataAddr(0);
+  } else if (RawObject::IsTypedDataClassId(class_id)) {
     // Regular typed data object, set up some GC and API callback guards.
     const TypedData& obj = Api::UnwrapTypedDataHandle(isolate, object);
     ASSERT(!obj.IsNull());
     *len = obj.Length();
     isolate->IncrementNoGCScopeDepth();
     START_NO_CALLBACK_SCOPE(isolate);
-    *data = reinterpret_cast<void*>(obj.DataAddr(0));
+    *data = obj.DataAddr(0);
+  } else {
+    // typed data view object, set up some GC and API callback guards.
+    // TODO(asiva): Have to come up with a scheme to directly access
+    // the fields using offsets for a more efficient implementation.
+    Dart_Handle field_name = Dart_NewStringFromCString("length");
+    Dart_Handle field_value = Dart_GetField(object, field_name);
+    ASSERT(Api::IsSmi(field_value));
+    *len = Api::SmiValue(field_value);
+    field_name = Dart_NewStringFromCString("offsetInBytes");
+    field_value = Dart_GetField(object, field_name);
+    ASSERT(Api::IsSmi(field_value));
+    intptr_t offset_in_bytes = Api::SmiValue(field_value);
+    field_name = Dart_NewStringFromCString("_typeddata");
+    field_value = Dart_GetField(object, field_name);
+    const TypedData& obj = Api::UnwrapTypedDataHandle(isolate, field_value);
+    isolate->IncrementNoGCScopeDepth();
+    START_NO_CALLBACK_SCOPE(isolate);
+    *data = obj.DataAddr(offset_in_bytes);
   }
   return Api::Success(isolate);
 }
@@ -2714,6 +2731,7 @@
   DARTSCOPE(isolate);
   intptr_t class_id = Api::ClassId(object);
   if (!RawObject::IsExternalTypedDataClassId(class_id) &&
+      !RawObject::IsTypedDataViewClassId(class_id) &&
       !RawObject::IsTypedDataClassId(class_id)) {
     RETURN_TYPE_ERROR(isolate, object, 'TypedData');
   }
@@ -4401,6 +4419,8 @@
   if (buffer == NULL) {
     RETURN_NULL_ERROR(buffer);
   }
+  NoHeapGrowthControlScope no_growth_control;
+
   const Snapshot* snapshot = Snapshot::SetupFromBuffer(buffer);
   if (!snapshot->IsScriptSnapshot()) {
     return Api::NewError("%s expects parameter 'buffer' to be a script type"
diff --git a/runtime/vm/dart_api_impl_test.cc b/runtime/vm/dart_api_impl_test.cc
index b86ab17..b66ede1 100644
--- a/runtime/vm/dart_api_impl_test.cc
+++ b/runtime/vm/dart_api_impl_test.cc
@@ -1032,14 +1032,16 @@
 static void TestDirectAccess(Dart_Handle lib,
                              Dart_Handle array,
                              Dart_TypedData_Type expected_type) {
+  Dart_Handle result;
+
   // Invoke the dart function that sets initial values.
   Dart_Handle dart_args[1];
   dart_args[0] = array;
-  Dart_Invoke(lib, NewString("setMain"), 1, dart_args);
+  result = Dart_Invoke(lib, NewString("setMain"), 1, dart_args);
+  EXPECT_VALID(result);
 
   // Now Get a direct access to this typed data object and check it's contents.
   const int kLength = 10;
-  Dart_Handle result;
   Dart_TypedData_Type type;
   void* data;
   intptr_t len;
@@ -1063,7 +1065,8 @@
   EXPECT_VALID(result);
 
   // Invoke the dart function in order to check the modified values.
-  Dart_Invoke(lib, NewString("testMain"), 1, dart_args);
+  result = Dart_Invoke(lib, NewString("testMain"), 1, dart_args);
+  EXPECT_VALID(result);
 }
 
 
@@ -1075,10 +1078,11 @@
       "    a[i] = i;"
       "  }"
       "}\n"
-      "void testMain(var list) {"
+      "bool testMain(var list) {"
       "  for (var i = 0; i < 10; i++) {"
       "    Expect.equals((10 + i), list[i]);"
       "  }\n"
+      "  return true;"
       "}\n"
       "List main() {"
       "  var a = new Int8List(10);"
@@ -1106,6 +1110,70 @@
 }
 
 
+TEST_CASE(TypedDataViewDirectAccess) {
+  const char* kScriptChars =
+      "import 'dart:typeddata';\n"
+      "void setMain(var list) {"
+      "  Expect.equals(10, list.length);"
+      "  for (var i = 0; i < 10; i++) {"
+      "    list[i] = i;"
+      "  }"
+      "}\n"
+      "bool testMain(var list) {"
+      "  Expect.equals(10, list.length);"
+      "  for (var i = 0; i < 10; i++) {"
+      "    Expect.equals((10 + i), list[i]);"
+      "  }"
+      "  return true;"
+      "}\n"
+      "List main() {"
+      "  var a = new Int8List(100);"
+      "  var view = new Int8List.view(a.buffer, 50, 10);"
+      "  return view;"
+      "}\n";
+  // Create a test library and Load up a test script in it.
+  Dart_Handle lib = TestCase::LoadTestScript(kScriptChars, NULL);
+
+  // Test with a typed data view object.
+  Dart_Handle list_access_test_obj;
+  list_access_test_obj = Dart_Invoke(lib, NewString("main"), 0, NULL);
+  EXPECT_VALID(list_access_test_obj);
+  TestDirectAccess(lib, list_access_test_obj, kInt8);
+}
+
+
+TEST_CASE(ByteDataDirectAccess) {
+  const char* kScriptChars =
+      "import 'dart:typeddata';\n"
+      "void setMain(var list) {"
+      "  Expect.equals(10, list.length);"
+      "  for (var i = 0; i < 10; i++) {"
+      "    list.setInt8(i, i);"
+      "  }"
+      "}\n"
+      "bool testMain(var list) {"
+      "  Expect.equals(10, list.length);"
+      "  for (var i = 0; i < 10; i++) {"
+      "    Expect.equals((10 + i), list.getInt8(i));"
+      "  }"
+      "  return true;"
+      "}\n"
+      "ByteData main() {"
+      "  var a = new Int8List(100);"
+      "  var view = new ByteData.view(a.buffer, 50, 10);"
+      "  return view;"
+      "}\n";
+  // Create a test library and Load up a test script in it.
+  Dart_Handle lib = TestCase::LoadTestScript(kScriptChars, NULL);
+
+  // Test with a typed data view object.
+  Dart_Handle list_access_test_obj;
+  list_access_test_obj = Dart_Invoke(lib, NewString("main"), 0, NULL);
+  EXPECT_VALID(list_access_test_obj);
+  TestDirectAccess(lib, list_access_test_obj, kByteData);
+}
+
+
 static void ExternalTypedDataAccessTests(Dart_Handle obj,
                                          Dart_TypedData_Type expected_type,
                                          uint8_t data[],
diff --git a/runtime/vm/dart_api_message.h b/runtime/vm/dart_api_message.h
index 7103fa1..84d44a8 100644
--- a/runtime/vm/dart_api_message.h
+++ b/runtime/vm/dart_api_message.h
@@ -119,10 +119,11 @@
 
 class ApiMessageWriter : public BaseWriter {
  public:
-  static const intptr_t kIncrementSize = 512;
+  static const intptr_t kInitialSize = 512;
   ApiMessageWriter(uint8_t** buffer, ReAlloc alloc)
-      : BaseWriter(buffer, alloc, kIncrementSize), object_id_(0),
-        forward_list_(NULL), forward_list_length_(0), forward_id_(0) {
+      : BaseWriter(buffer, alloc, kInitialSize),
+        object_id_(0), forward_list_(NULL),
+        forward_list_length_(0), forward_id_(0) {
     ASSERT(kDartCObjectTypeMask >= Dart_CObject::kNumberOfTypes - 1);
   }
   ~ApiMessageWriter() {
diff --git a/runtime/vm/datastream.h b/runtime/vm/datastream.h
index 652d942..1aa299b 100644
--- a/runtime/vm/datastream.h
+++ b/runtime/vm/datastream.h
@@ -136,22 +136,22 @@
 // Stream for writing various types into a buffer.
 class WriteStream : public ValueObject {
  public:
-  WriteStream(uint8_t** buffer, ReAlloc alloc, intptr_t increment_size) :
+  WriteStream(uint8_t** buffer, ReAlloc alloc, intptr_t initial_size) :
       buffer_(buffer),
       end_(NULL),
       current_(NULL),
       current_size_(0),
       alloc_(alloc),
-      increment_size_(increment_size) {
+      initial_size_(initial_size) {
     ASSERT(buffer != NULL);
     ASSERT(alloc != NULL);
     *buffer_ = reinterpret_cast<uint8_t*>(alloc_(NULL,
                                                  0,
-                                                 increment_size_));
+                                                 initial_size_));
     ASSERT(*buffer_ != NULL);
     current_ = *buffer_;
-    current_size_ = increment_size_;
-    end_ = *buffer_ + increment_size_;
+    current_size_ = initial_size_;
+    end_ = *buffer_ + initial_size_;
   }
 
   uint8_t* buffer() const { return *buffer_; }
@@ -234,8 +234,12 @@
 
   void Resize(intptr_t size_needed) {
     intptr_t position = current_ - *buffer_;
-    intptr_t new_size = current_size_ +
-        Utils::RoundUp(size_needed, increment_size_);
+    intptr_t increment_size = current_size_;
+    if (size_needed > increment_size) {
+      increment_size = Utils::RoundUp(size_needed, initial_size_);
+    }
+    intptr_t new_size = current_size_ + increment_size;
+    ASSERT(new_size > current_size_);
     *buffer_ = reinterpret_cast<uint8_t*>(alloc_(*buffer_,
                                                  current_size_,
                                                  new_size));
@@ -252,7 +256,7 @@
   uint8_t* current_;
   intptr_t current_size_;
   ReAlloc alloc_;
-  intptr_t increment_size_;
+  intptr_t initial_size_;
 
   DISALLOW_COPY_AND_ASSIGN(WriteStream);
 };
diff --git a/runtime/vm/debugger_api_impl_test.cc b/runtime/vm/debugger_api_impl_test.cc
index 3d61b7b..81e9c9d 100644
--- a/runtime/vm/debugger_api_impl_test.cc
+++ b/runtime/vm/debugger_api_impl_test.cc
@@ -34,7 +34,7 @@
                         NewString(cname),
                         NewString(fname),
                         &bpt);
-  EXPECT_VALID(res);
+  EXPECT_TRUE(res);
 }
 
 
@@ -58,14 +58,14 @@
   static char info_str[128];
   Dart_ActivationFrame frame;
   Dart_Handle res = Dart_GetActivationFrame(trace, 0, &frame);
-  EXPECT_VALID(res);
+  EXPECT_TRUE(res);
   Dart_Handle func_name;
   Dart_Handle url;
   intptr_t line_number = 0;
   intptr_t library_id = 0;
   res = Dart_ActivationFrameInfo(
             frame, &func_name, &url, &line_number, &library_id);
-  EXPECT_VALID(res);
+  EXPECT_TRUE(res);
   OS::SNPrint(info_str, sizeof(info_str), "function %s (%s:%"Pd")",
               ToCString(func_name), ToCString(url), line_number);
   return info_str;
@@ -133,7 +133,7 @@
   Dart_Handle func_name;
   Dart_Handle res;
   res = Dart_ActivationFrameInfo(frame, &func_name, NULL, NULL, NULL);
-  EXPECT_VALID(res);
+  EXPECT_TRUE(res);
   EXPECT(Dart_IsString(func_name));
   const char* func_name_chars;
   Dart_StringToCString(func_name, &func_name_chars);
@@ -159,11 +159,11 @@
 static void PrintStackTrace(Dart_StackTrace trace) {
   intptr_t trace_len;
   Dart_Handle res = Dart_StackTraceLength(trace, &trace_len);
-  EXPECT_VALID(res);
+  EXPECT_TRUE(res);
   for (int i = 0; i < trace_len; i++) {
     Dart_ActivationFrame frame;
     res = Dart_GetActivationFrame(trace, i, &frame);
-    EXPECT_VALID(res);
+    EXPECT_TRUE(res);
     PrintActivationFrame(frame);
   }
 }
@@ -202,7 +202,7 @@
   Dart_Handle func_name;
   Dart_Handle res;
   res = Dart_ActivationFrameInfo(frame, &func_name, NULL, NULL, NULL);
-  EXPECT_VALID(res);
+  EXPECT_TRUE(res);
   EXPECT(Dart_IsString(func_name));
   const char* func_name_chars;
   Dart_StringToCString(func_name, &func_name_chars);
@@ -225,11 +225,11 @@
                              bool skip_null_expects) {
   intptr_t trace_len;
   Dart_Handle res = Dart_StackTraceLength(trace, &trace_len);
-  EXPECT_VALID(res);
+  EXPECT_TRUE(res);
   for (int i = 0; i < trace_len; i++) {
     Dart_ActivationFrame frame;
     res = Dart_GetActivationFrame(trace, i, &frame);
-    EXPECT_VALID(res);
+    EXPECT_TRUE(res);
     if (i < expected_frames) {
       VerifyStackFrame(frame, func_names[i], local_vars[i], skip_null_expects);
     } else {
diff --git a/runtime/vm/disassembler_test.cc b/runtime/vm/disassembler_test.cc
index 56ac9bd..1c33942 100644
--- a/runtime/vm/disassembler_test.cc
+++ b/runtime/vm/disassembler_test.cc
@@ -9,10 +9,6 @@
 
 namespace dart {
 
-// Disassembler only supported on IA32, X64, and ARM.
-#if defined(TARGET_ARCH_IA32) ||                                               \
-    defined(TARGET_ARCH_X64) ||                                                \
-    defined(TARGET_ARCH_ARM)
 TEST_CASE(Disassembler) {
   Assembler assembler;
   // The used instructions work on all platforms.
@@ -25,6 +21,5 @@
   test.Assemble();
   Disassembler::Disassemble(test.entry(), test.entry() + assembler.CodeSize());
 }
-#endif
 
 }  // namespace dart
diff --git a/runtime/vm/disassembler_x64.cc b/runtime/vm/disassembler_x64.cc
index e17c4f0..4af7ba3 100644
--- a/runtime/vm/disassembler_x64.cc
+++ b/runtime/vm/disassembler_x64.cc
@@ -70,7 +70,7 @@
   { 0x39, OPER_REG_OP_ORDER,      "cmp" },
   { 0x3A, BYTE_REG_OPER_OP_ORDER, "cmp" },
   { 0x3B, REG_OPER_OP_ORDER,      "cmp" },
-  { 0x63, REG_OPER_OP_ORDER,      "movsxlq" },
+  { 0x63, REG_OPER_OP_ORDER,      "movsxd" },
   { 0x84, BYTE_REG_OPER_OP_ORDER, "test" },
   { 0x85, REG_OPER_OP_ORDER,      "test" },
   { 0x86, BYTE_REG_OPER_OP_ORDER, "xchg" },
diff --git a/runtime/vm/flow_graph_builder.cc b/runtime/vm/flow_graph_builder.cc
index 7eb6581..2dcce7c 100644
--- a/runtime/vm/flow_graph_builder.cc
+++ b/runtime/vm/flow_graph_builder.cc
@@ -1802,23 +1802,23 @@
 
 static intptr_t GetResultCidOfNative(const Function& function) {
   const Class& function_class = Class::Handle(function.Owner());
-  if (function_class.library() == Library::ScalarlistLibrary()) {
+  if (function_class.library() == Library::TypedDataLibrary()) {
     const String& function_name = String::Handle(function.name());
     if (!String::EqualsIgnoringPrivateKey(function_name, Symbols::_New())) {
       return kDynamicCid;
     }
     switch (function_class.id()) {
-      case kInt8ArrayCid:
-      case kUint8ArrayCid:
-      case kUint8ClampedArrayCid:
-      case kInt16ArrayCid:
-      case kUint16ArrayCid:
-      case kInt32ArrayCid:
-      case kUint32ArrayCid:
-      case kInt64ArrayCid:
-      case kUint64ArrayCid:
-      case kFloat32ArrayCid:
-      case kFloat64ArrayCid:
+      case kTypedDataInt8ArrayCid:
+      case kTypedDataUint8ArrayCid:
+      case kTypedDataUint8ClampedArrayCid:
+      case kTypedDataInt16ArrayCid:
+      case kTypedDataUint16ArrayCid:
+      case kTypedDataInt32ArrayCid:
+      case kTypedDataUint32ArrayCid:
+      case kTypedDataInt64ArrayCid:
+      case kTypedDataUint64ArrayCid:
+      case kTypedDataFloat32ArrayCid:
+      case kTypedDataFloat64ArrayCid:
         return function_class.id();
       default:
         return kDynamicCid;  // Unknown.
@@ -1978,18 +1978,18 @@
 #define RECOGNIZED_LIST_FACTORY_LIST(V)                                        \
   V(ObjectArrayFactory, kArrayCid, 97987288)                                   \
   V(GrowableObjectArrayWithData, kGrowableObjectArrayCid, 816132033)           \
-  V(GrowableObjectArrayFactory, kGrowableObjectArrayCid, 1896741574)           \
-  V(Int8ListFactory, kInt8ArrayCid, 817410959)                                 \
-  V(Uint8ListFactory, kUint8ArrayCid, 220896178)                               \
-  V(Uint8ClampedListFactory, kUint8ClampedArrayCid, 422034060)                 \
-  V(Int16ListFactory, kInt16ArrayCid, 214246025)                               \
-  V(Uint16ListFactory, kUint16ArrayCid, 137929963)                             \
-  V(Int32ListFactory, kInt32ArrayCid, 1977571010)                              \
-  V(Uint32ListFactory, kUint32ArrayCid, 407638944)                             \
-  V(Int64ListFactory, kInt64ArrayCid, 885130273)                               \
-  V(Uint64ListFactory, kUint64ArrayCid, 1471017221)                            \
-  V(Float64ListFactory, kFloat64ArrayCid, 1037441059)                          \
-  V(Float32ListFactory, kFloat32ArrayCid, 2035252095)                          \
+  V(GrowableObjectArrayFactory, kGrowableObjectArrayCid, 224791427)            \
+  V(Int8ListFactory, kTypedDataInt8ArrayCid, 1178498933)                       \
+  V(Uint8ListFactory, kTypedDataUint8ArrayCid, 996047641)                      \
+  V(Uint8ClampedListFactory, kTypedDataUint8ClampedArrayCid, 1504313643)       \
+  V(Int16ListFactory, kTypedDataInt16ArrayCid, 1595869856)                     \
+  V(Uint16ListFactory, kTypedDataUint16ArrayCid, 665298027)                    \
+  V(Int32ListFactory, kTypedDataInt32ArrayCid, 728173538)                      \
+  V(Uint32ListFactory, kTypedDataUint32ArrayCid, 352036624)                    \
+  V(Int64ListFactory, kTypedDataInt64ArrayCid, 105935265)                      \
+  V(Uint64ListFactory, kTypedDataUint64ArrayCid, 943403644)                    \
+  V(Float64ListFactory, kTypedDataFloat64ArrayCid, 348533743)                  \
+  V(Float32ListFactory, kTypedDataFloat32ArrayCid, 1830794379)                 \
 
 
 // Class that recognizes factories and returns corresponding result cid.
@@ -2001,7 +2001,7 @@
     const Class& function_class = Class::Handle(factory.Owner());
     const Library& lib = Library::Handle(function_class.library());
     ASSERT((lib.raw() == Library::CoreLibrary()) ||
-        (lib.raw() == Library::ScalarlistLibrary()));
+        (lib.raw() == Library::TypedDataLibrary()));
     const String& factory_name = String::Handle(factory.name());
 #define RECOGNIZE_FACTORY(test_factory_symbol, cid, fp)                        \
     if (String::EqualsIgnoringPrivateKey(                                      \
@@ -2023,7 +2023,7 @@
   const Class& function_class = Class::Handle(function.Owner());
 
   if ((function_class.library() != Library::CoreLibrary()) &&
-      (function_class.library() != Library::ScalarlistLibrary())) {
+      (function_class.library() != Library::TypedDataLibrary())) {
     return kDynamicCid;
   }
 
diff --git a/runtime/vm/flow_graph_compiler.cc b/runtime/vm/flow_graph_compiler.cc
index 37eff8b5..791412d 100644
--- a/runtime/vm/flow_graph_compiler.cc
+++ b/runtime/vm/flow_graph_compiler.cc
@@ -953,32 +953,10 @@
     case kArrayCid:
     case kImmutableArrayCid:
       return Array::kBytesPerElement;
-    case kFloat32ArrayCid:
-      return Float32Array::kBytesPerElement;
-    case kFloat64ArrayCid:
-      return Float64Array::kBytesPerElement;
-    case kInt8ArrayCid:
-      return Int8Array::kBytesPerElement;
-    case kUint8ArrayCid:
-      return Uint8Array::kBytesPerElement;
-    case kUint8ClampedArrayCid:
-      return Uint8ClampedArray::kBytesPerElement;
-    case kInt16ArrayCid:
-      return Int16Array::kBytesPerElement;
-    case kUint16ArrayCid:
-      return Uint16Array::kBytesPerElement;
-    case kInt32ArrayCid:
-      return Int32Array::kBytesPerElement;
-    case kUint32ArrayCid:
-      return Uint32Array::kBytesPerElement;
     case kOneByteStringCid:
       return OneByteString::kBytesPerElement;
     case kTwoByteStringCid:
       return TwoByteString::kBytesPerElement;
-    case kExternalUint8ArrayCid:
-      return ExternalUint8Array::kBytesPerElement;
-    case kExternalUint8ClampedArrayCid:
-      return ExternalUint8ClampedArray::kBytesPerElement;
     default:
       UNIMPLEMENTED();
       return 0;
@@ -998,32 +976,10 @@
     case kArrayCid:
     case kImmutableArrayCid:
       return Array::data_offset();
-    case kFloat32ArrayCid:
-      return Float32Array::data_offset();
-    case kFloat64ArrayCid:
-      return Float64Array::data_offset();
-    case kInt8ArrayCid:
-      return Int8Array::data_offset();
-    case kUint8ArrayCid:
-      return Uint8Array::data_offset();
-    case kUint8ClampedArrayCid:
-      return Uint8ClampedArray::data_offset();
-    case kInt16ArrayCid:
-      return Int16Array::data_offset();
-    case kUint16ArrayCid:
-      return Uint16Array::data_offset();
-    case kInt32ArrayCid:
-      return Int32Array::data_offset();
-    case kUint32ArrayCid:
-      return Uint32Array::data_offset();
     case kOneByteStringCid:
       return OneByteString::data_offset();
     case kTwoByteStringCid:
       return TwoByteString::data_offset();
-    case kExternalUint8ArrayCid:
-    case kExternalUint8ClampedArrayCid:
-      // Elements start at offset 0 of the external data.
-      return 0;
     default:
       UNIMPLEMENTED();
       return Array::data_offset();
diff --git a/runtime/vm/flow_graph_compiler_arm.cc b/runtime/vm/flow_graph_compiler_arm.cc
index 7fb6ecb..ecbb548 100644
--- a/runtime/vm/flow_graph_compiler_arm.cc
+++ b/runtime/vm/flow_graph_compiler_arm.cc
@@ -23,6 +23,7 @@
 DECLARE_FLAG(bool, print_ast);
 DECLARE_FLAG(bool, print_scopes);
 DECLARE_FLAG(bool, enable_type_checks);
+DECLARE_FLAG(bool, eliminate_type_checks);
 
 
 FlowGraphCompiler::~FlowGraphCompiler() {
@@ -82,17 +83,75 @@
                                       const GrowableArray<intptr_t>& class_ids,
                                       Label* is_equal_lbl,
                                       Label* is_not_equal_lbl) {
-  UNIMPLEMENTED();
+  for (intptr_t i = 0; i < class_ids.length(); i++) {
+    __ CompareImmediate(class_id_reg, class_ids[i]);
+    __ b(is_equal_lbl, EQ);
+  }
+  __ b(is_not_equal_lbl);
 }
 
 
+// Testing against an instantiated type with no arguments, without
+// SubtypeTestCache.
+// R0: instance being type checked (preserved).
+// Clobbers R2, R3.
+// Returns true if there is a fallthrough.
 bool FlowGraphCompiler::GenerateInstantiatedTypeNoArgumentsTest(
     intptr_t token_pos,
     const AbstractType& type,
     Label* is_instance_lbl,
     Label* is_not_instance_lbl) {
-  UNIMPLEMENTED();
-  return false;
+  __ Comment("InstantiatedTypeNoArgumentsTest");
+  ASSERT(type.IsInstantiated());
+  const Class& type_class = Class::Handle(type.type_class());
+  ASSERT(!type_class.HasTypeArguments());
+
+  const Register kInstanceReg = R0;
+  __ tst(kInstanceReg, ShifterOperand(kSmiTagMask));
+  // If instance is Smi, check directly.
+  const Class& smi_class = Class::Handle(Smi::Class());
+  if (smi_class.IsSubtypeOf(TypeArguments::Handle(),
+                            type_class,
+                            TypeArguments::Handle(),
+                            NULL)) {
+    __ b(is_instance_lbl, EQ);
+  } else {
+    __ b(is_not_instance_lbl, EQ);
+  }
+  // Compare if the classes are equal.
+  const Register kClassIdReg = R2;
+  __ LoadClassId(kClassIdReg, kInstanceReg);
+  __ CompareImmediate(kClassIdReg, type_class.id());
+  __ b(is_instance_lbl, EQ);
+  // See ClassFinalizer::ResolveSuperTypeAndInterfaces for list of restricted
+  // interfaces.
+  // Bool interface can be implemented only by core class Bool.
+  if (type.IsBoolType()) {
+    __ CompareImmediate(kClassIdReg, kBoolCid);
+    __ b(is_instance_lbl, EQ);
+    __ b(is_not_instance_lbl);
+    return false;
+  }
+  if (type.IsFunctionType()) {
+    // Check if instance is a closure.
+    __ LoadClassById(R3, kClassIdReg);
+    __ ldr(R3, FieldAddress(R3, Class::signature_function_offset()));
+    __ CompareImmediate(R3, reinterpret_cast<int32_t>(Object::null()));
+    __ b(is_instance_lbl, NE);
+  }
+  // Custom checking for numbers (Smi, Mint, Bigint and Double).
+  // Note that instance is not Smi (checked above).
+  if (type.IsSubtypeOf(Type::Handle(Type::Number()), NULL)) {
+    GenerateNumberTypeCheck(
+        kClassIdReg, type, is_instance_lbl, is_not_instance_lbl);
+    return false;
+  }
+  if (type.IsStringType()) {
+    GenerateStringTypeCheck(kClassIdReg, is_instance_lbl, is_not_instance_lbl);
+    return false;
+  }
+  // Otherwise fallthrough.
+  return true;
 }
 
 
@@ -116,13 +175,70 @@
 }
 
 
+// Inputs:
+// - R0: instance being type checked (preserved).
+// - R1: optional instantiator type arguments (preserved).
+// Clobbers R2, R3.
+// Returns:
+// - preserved instance in R0 and optional instantiator type arguments in R1.
+// Note that this inlined code must be followed by the runtime_call code, as it
+// may fall through to it. Otherwise, this inline code will jump to the label
+// is_instance or to the label is_not_instance.
 RawSubtypeTestCache* FlowGraphCompiler::GenerateInlineInstanceof(
     intptr_t token_pos,
     const AbstractType& type,
     Label* is_instance_lbl,
     Label* is_not_instance_lbl) {
-  UNIMPLEMENTED();
-  return NULL;
+  __ Comment("InlineInstanceof");
+  if (type.IsVoidType()) {
+    // A non-null value is returned from a void function, which will result in a
+    // type error. A null value is handled prior to executing this inline code.
+    return SubtypeTestCache::null();
+  }
+  if (TypeCheckAsClassEquality(type)) {
+    const intptr_t type_cid = Class::Handle(type.type_class()).id();
+    const Register kInstanceReg = R0;
+    __ tst(kInstanceReg, ShifterOperand(kSmiTagMask));
+    if (type_cid == kSmiCid) {
+      __ b(is_instance_lbl, EQ);
+    } else {
+      __ b(is_not_instance_lbl, EQ);
+      __ CompareClassId(kInstanceReg, type_cid, R3);
+      __ b(is_instance_lbl, EQ);
+    }
+    __ b(is_not_instance_lbl);
+    return SubtypeTestCache::null();
+  }
+  if (type.IsInstantiated()) {
+    const Class& type_class = Class::ZoneHandle(type.type_class());
+    // A Smi object cannot be the instance of a parameterized class.
+    // A class equality check is only applicable with a dst type of a
+    // non-parameterized class or with a raw dst type of a parameterized class.
+    if (type_class.HasTypeArguments()) {
+      return GenerateInstantiatedTypeWithArgumentsTest(token_pos,
+                                                       type,
+                                                       is_instance_lbl,
+                                                       is_not_instance_lbl);
+      // Fall through to runtime call.
+    }
+    const bool has_fall_through =
+        GenerateInstantiatedTypeNoArgumentsTest(token_pos,
+                                                type,
+                                                is_instance_lbl,
+                                                is_not_instance_lbl);
+    if (has_fall_through) {
+      // If test non-conclusive so far, try the inlined type-test cache.
+      // 'type' is known at compile time.
+      return GenerateSubtype1TestCacheLookup(
+          token_pos, type_class, is_instance_lbl, is_not_instance_lbl);
+    } else {
+      return SubtypeTestCache::null();
+    }
+  }
+  return GenerateUninstantiatedTypeTest(token_pos,
+                                        type,
+                                        is_instance_lbl,
+                                        is_not_instance_lbl);
 }
 
 
@@ -135,12 +251,90 @@
 }
 
 
+// Optimize assignable type check by adding inlined tests for:
+// - NULL -> return NULL.
+// - Smi -> compile time subtype check (only if dst class is not parameterized).
+// - Class equality (only if class is not parameterized).
+// Inputs:
+// - R0: instance being type checked.
+// - R1: instantiator type arguments or raw_null.
+// - R2: instantiator or raw_null.
+// Returns:
+// - object in R0 for successful assignable check (or throws TypeError).
+// Performance notes: positive checks must be quick, negative checks can be slow
+// as they throw an exception.
 void FlowGraphCompiler::GenerateAssertAssignable(intptr_t token_pos,
                                                  intptr_t deopt_id,
                                                  const AbstractType& dst_type,
                                                  const String& dst_name,
                                                  LocationSummary* locs) {
-  UNIMPLEMENTED();
+  ASSERT(token_pos >= 0);
+  ASSERT(!dst_type.IsNull());
+  ASSERT(dst_type.IsFinalized());
+  // Assignable check is skipped in FlowGraphBuilder, not here.
+  ASSERT(dst_type.IsMalformed() ||
+         (!dst_type.IsDynamicType() && !dst_type.IsObjectType()));
+  // Preserve instantiator and its type arguments.
+  __ PushList((1 << R1) | (1 << R2));
+  // A null object is always assignable and is returned as result.
+  Label is_assignable, runtime_call;
+  __ CompareImmediate(R0, reinterpret_cast<int32_t>(Object::null()));
+  __ b(&is_assignable, EQ);
+
+  if (!FLAG_eliminate_type_checks) {
+    // If type checks are not eliminated during the graph building then
+    // a transition sentinel can be seen here.
+    __ CompareObject(R0, Object::transition_sentinel());
+    __ b(&is_assignable, EQ);
+  }
+
+  // Generate throw new TypeError() if the type is malformed.
+  if (dst_type.IsMalformed()) {
+    const Error& error = Error::Handle(dst_type.malformed_error());
+    const String& error_message = String::ZoneHandle(
+        Symbols::New(error.ToErrorCString()));
+    __ PushObject(Object::ZoneHandle());  // Make room for the result.
+    __ Push(R0);  // Push the source object.
+    __ PushObject(dst_name);  // Push the name of the destination.
+    __ PushObject(error_message);
+    GenerateCallRuntime(token_pos,
+                        deopt_id,
+                        kMalformedTypeErrorRuntimeEntry,
+                        locs);
+    // We should never return here.
+    __ bkpt(0);
+
+    __ Bind(&is_assignable);  // For a null object.
+    // Restore instantiator and its type arguments.
+    __ PopList((1 << R1) | (1 << R2));
+    return;
+  }
+
+  // Generate inline type check, linking to runtime call if not assignable.
+  SubtypeTestCache& test_cache = SubtypeTestCache::ZoneHandle();
+  test_cache = GenerateInlineInstanceof(token_pos, dst_type,
+                                        &is_assignable, &runtime_call);
+
+  __ Bind(&runtime_call);
+  // Load instantiator and its type arguments.
+  __ ldm(IA, SP,  (1 << R1) | (1 << R2));
+  __ PushObject(Object::ZoneHandle());  // Make room for the result.
+  __ Push(R0);  // Push the source object.
+  __ PushObject(dst_type);  // Push the type of the destination.
+  // Push instantiator and its type arguments.
+  __ PushList((1 << R1) | (1 << R2));
+  __ PushObject(dst_name);  // Push the name of the destination.
+  __ LoadObject(R0, test_cache);
+  __ Push(R0);
+  GenerateCallRuntime(token_pos, deopt_id, kTypeCheckRuntimeEntry, locs);
+  // Pop the parameters supplied to the runtime entry. The result of the
+  // type check runtime call is the checked value.
+  __ Drop(6);
+  __ Pop(R0);
+
+  __ Bind(&is_assignable);
+  // Restore instantiator and its type arguments.
+  __ PopList((1 << R1) | (1 << R2));
 }
 
 
@@ -663,8 +857,8 @@
                                          intptr_t deopt_id,
                                          intptr_t token_pos,
                                          LocationSummary* locs) {
-  __ LoadObject(R5, ic_data);
   __ LoadObject(R4, arguments_descriptor);
+  __ LoadObject(R5, ic_data);
   GenerateDartCall(deopt_id,
                    token_pos,
                    target_label,
diff --git a/runtime/vm/flow_graph_compiler_ia32.cc b/runtime/vm/flow_graph_compiler_ia32.cc
index b9e8bb4..37e3f3d 100644
--- a/runtime/vm/flow_graph_compiler_ia32.cc
+++ b/runtime/vm/flow_graph_compiler_ia32.cc
@@ -229,8 +229,9 @@
   __ LoadClassId(kClassIdReg, kInstanceReg);
   __ cmpl(kClassIdReg, Immediate(type_class.id()));
   __ j(EQUAL, is_instance_lbl);
+  // See ClassFinalizer::ResolveSuperTypeAndInterfaces for list of restricted
+  // interfaces.
   // Bool interface can be implemented only by core class Bool.
-  // (see ClassFinalizer::ResolveInterfaces for list of restricted interfaces).
   if (type.IsBoolType()) {
     __ cmpl(kClassIdReg, Immediate(kBoolCid));
     __ j(EQUAL, is_instance_lbl);
diff --git a/runtime/vm/flow_graph_compiler_x64.cc b/runtime/vm/flow_graph_compiler_x64.cc
index d67ef15..bc5181d 100644
--- a/runtime/vm/flow_graph_compiler_x64.cc
+++ b/runtime/vm/flow_graph_compiler_x64.cc
@@ -228,8 +228,9 @@
   __ LoadClassId(kClassIdReg, kInstanceReg);
   __ cmpl(kClassIdReg, Immediate(type_class.id()));
   __ j(EQUAL, is_instance_lbl);
+  // See ClassFinalizer::ResolveSuperTypeAndInterfaces for list of restricted
+  // interfaces.
   // Bool interface can be implemented only by core class Bool.
-  // (see ClassFinalizer::ResolveInterfaces for list of restricted interfaces).
   if (type.IsBoolType()) {
     __ cmpl(kClassIdReg, Immediate(kBoolCid));
     __ j(EQUAL, is_instance_lbl);
diff --git a/runtime/vm/flow_graph_optimizer.cc b/runtime/vm/flow_graph_optimizer.cc
index 9e6ee4e..45c00d8 100644
--- a/runtime/vm/flow_graph_optimizer.cc
+++ b/runtime/vm/flow_graph_optimizer.cc
@@ -19,22 +19,23 @@
 
 namespace dart {
 
-DECLARE_FLAG(bool, eliminate_type_checks);
-DECLARE_FLAG(bool, enable_type_checks);
-DEFINE_FLAG(bool, trace_optimization, false, "Print optimization details.");
-DECLARE_FLAG(bool, trace_type_check_elimination);
-DEFINE_FLAG(bool, use_cha, true, "Use class hierarchy analysis.");
-DEFINE_FLAG(bool, load_cse, true, "Use redundant load elimination.");
-DEFINE_FLAG(bool, trace_range_analysis, false, "Trace range analysis progress");
-DEFINE_FLAG(bool, trace_constant_propagation, false,
-    "Print constant propagation and useless code elimination.");
 DEFINE_FLAG(bool, array_bounds_check_elimination, true,
     "Eliminate redundant bounds checks.");
+DEFINE_FLAG(bool, load_cse, true, "Use redundant load elimination.");
 DEFINE_FLAG(int, max_polymorphic_checks, 4,
     "Maximum number of polymorphic check, otherwise it is megamorphic.");
 DEFINE_FLAG(bool, remove_redundant_phis, true, "Remove redundant phis.");
+DEFINE_FLAG(bool, trace_constant_propagation, false,
+    "Print constant propagation and useless code elimination.");
+DEFINE_FLAG(bool, trace_optimization, false, "Print optimization details.");
+DEFINE_FLAG(bool, trace_range_analysis, false, "Trace range analysis progress");
 DEFINE_FLAG(bool, truncating_left_shift, true,
     "Optimize left shift to truncate if possible");
+DEFINE_FLAG(bool, use_cha, true, "Use class hierarchy analysis.");
+DECLARE_FLAG(bool, eliminate_type_checks);
+DECLARE_FLAG(bool, enable_type_checks);
+DECLARE_FLAG(bool, trace_type_check_elimination);
+
 
 
 void FlowGraphOptimizer::ApplyICData() {
@@ -89,8 +90,10 @@
     intptr_t cid = call->PushArgumentAt(i)->value()->Type()->ToCid();
     class_ids.Add(cid);
   }
-  // TODO(srdjan): Test for other class_ids > 1.
-  if (class_ids.length() != 1) return false;
+  // TODO(srdjan): Test for number of arguments checked greater than 1.
+  if (class_ids.length() != 1) {
+    return false;
+  }
   if (class_ids[0] != kDynamicCid) {
     const intptr_t num_named_arguments = call->argument_names().IsNull() ?
         0 : call->argument_names().Length();
@@ -813,9 +816,7 @@
       case kTypedDataFloat32ArrayCid:
       case kTypedDataFloat64ArrayCid: {
         type_args = instantiator = flow_graph_->constant_null();
-        ASSERT((class_id != kFloat32ArrayCid &&
-                class_id != kFloat64ArrayCid &&
-                class_id != kTypedDataFloat32ArrayCid &&
+        ASSERT((class_id != kTypedDataFloat32ArrayCid &&
                 class_id != kTypedDataFloat64ArrayCid) ||
                value_type.IsDoubleType());
         ASSERT(value_type.IsInstantiated());
@@ -842,9 +843,10 @@
   intptr_t array_cid = PrepareIndexedOp(call, class_id, &array, &index);
   // Check if store barrier is needed. Byte arrays don't need a store barrier.
   StoreBarrierType needs_store_barrier =
-      RawObject::IsByteArrayClassId(array_cid)
-          ? kNoStoreBarrier
-          : kEmitStoreBarrier;
+      (RawObject::IsTypedDataClassId(array_cid) ||
+       RawObject::IsTypedDataViewClassId(array_cid) ||
+       RawObject::IsExternalTypedDataClassId(array_cid)) ? kNoStoreBarrier
+                                                         : kEmitStoreBarrier;
   if (!value_check.IsNull()) {
     // No store barrier needed because checked value is a smi, an unboxed mint
     // or unboxed double.
@@ -1620,7 +1622,8 @@
   // loads on ia32 like we do for normal array loads, and only revert to
   // mint case after deoptimizing here.
   intptr_t deopt_id = Isolate::kNoDeoptId;
-  if ((view_cid == kInt32ArrayCid || view_cid == kUint32ArrayCid) &&
+  if ((view_cid == kTypedDataInt32ArrayCid ||
+       view_cid == kTypedDataUint32ArrayCid) &&
       call->ic_data()->deopt_reason() == kDeoptUnknown) {
     deopt_id = call->deopt_id();
   }
@@ -2345,22 +2348,6 @@
   }
 }
 
-// For a comparison operation return an operation for the negated comparison:
-// !(a (op) b) === a (op') b
-static Token::Kind NegateComparison(Token::Kind op) {
-  switch (op) {
-    case Token::kEQ: return Token::kNE;
-    case Token::kNE: return Token::kEQ;
-    case Token::kLT: return Token::kGTE;
-    case Token::kGT: return Token::kLTE;
-    case Token::kLTE: return Token::kGT;
-    case Token::kGTE: return Token::kLT;
-    default:
-      UNREACHABLE();
-      return Token::kILLEGAL;
-  }
-}
-
 
 // Given a boundary (right operand) and a comparison operation return
 // a symbolic range constraint for the left operand of the comparison assuming
@@ -2440,7 +2427,7 @@
     ConstraintInstr* false_constraint =
         InsertConstraintFor(
             defn,
-            ConstraintRange(NegateComparison(op_kind), boundary),
+            ConstraintRange(Token::NegateComparison(op_kind), boundary),
             branch->false_successor());
     // Mark false_constraint an artificial use of boundary. This ensures
     // that constraint's range is recalculated if boundary's range changes.
@@ -3128,7 +3115,7 @@
             StoreIndexedInstr* array_store = instr->AsStoreIndexed();
             if (array_store == NULL ||
                 array_store->class_id() == kArrayCid ||
-                array_store->class_id() == kFloat64ArrayCid) {
+                array_store->class_id() == kTypedDataFloat64ArrayCid) {
               Definition* load = map_->Lookup(instr->AsDefinition());
               if (load != NULL) {
                 // Store has a corresponding numbered load. Try forwarding
diff --git a/runtime/vm/flow_graph_type_propagator.cc b/runtime/vm/flow_graph_type_propagator.cc
index 2e2fcd5..52fd2e2 100644
--- a/runtime/vm/flow_graph_type_propagator.cc
+++ b/runtime/vm/flow_graph_type_propagator.cc
@@ -407,14 +407,18 @@
     cid_ = kDynamicCid;
   }
 
-  if (ToAbstractType()->IsMoreSpecificThan(*other->ToAbstractType(), NULL)) {
+  Error& malformed_error = Error::Handle();
+  if (ToAbstractType()->IsMoreSpecificThan(*other->ToAbstractType(),
+                                           &malformed_error)) {
     type_ = other->ToAbstractType();
-  } else if (ToAbstractType()->IsMoreSpecificThan(*ToAbstractType(), NULL)) {
+  } else if (ToAbstractType()->IsMoreSpecificThan(*ToAbstractType(),
+                                                  &malformed_error)) {
     // Nothing to do.
   } else {
     // Can't unify.
     type_ = &Type::ZoneHandle(Type::DynamicType());
   }
+  ASSERT(malformed_error.IsNull());
 }
 
 
@@ -597,7 +601,10 @@
     return IsNull();
   }
 
-  return ToAbstractType()->IsMoreSpecificThan(other, NULL);
+  Error& malformed_error = Error::Handle();
+  const bool is_more_specific =
+      ToAbstractType()->IsMoreSpecificThan(other, &malformed_error);
+  return malformed_error.IsNull() && is_more_specific;
 }
 
 
diff --git a/runtime/vm/heap.cc b/runtime/vm/heap.cc
index 7cf859f..0809917 100644
--- a/runtime/vm/heap.cc
+++ b/runtime/vm/heap.cc
@@ -201,8 +201,13 @@
 }
 
 
-void Heap::EnableGrowthControl() {
-  old_space_->EnableGrowthControl();
+void Heap::SetGrowthControlState(bool state) {
+  old_space_->SetGrowthControlState(state);
+}
+
+
+bool Heap::GrowthControlState() {
+  return old_space_->GrowthControlState();
 }
 
 
@@ -482,4 +487,18 @@
 }
 #endif  // defined(DEBUG)
 
+
+NoHeapGrowthControlScope::NoHeapGrowthControlScope()
+    : StackResource(Isolate::Current()) {
+    Heap* heap = reinterpret_cast<Isolate*>(isolate())->heap();
+    current_growth_controller_state_ = heap->GrowthControlState();
+    heap->DisableGrowthControl();
+}
+
+
+NoHeapGrowthControlScope::~NoHeapGrowthControlScope() {
+    Heap* heap = reinterpret_cast<Isolate*>(isolate())->heap();
+    heap->SetGrowthControlState(current_growth_controller_state_);
+}
+
 }  // namespace dart
diff --git a/runtime/vm/heap.h b/runtime/vm/heap.h
index 3090efa..ab0f5db 100644
--- a/runtime/vm/heap.h
+++ b/runtime/vm/heap.h
@@ -132,7 +132,10 @@
 
   // Enables growth control on the page space heaps.  This should be
   // called before any user code is executed.
-  void EnableGrowthControl();
+  void EnableGrowthControl() { SetGrowthControlState(true); }
+  void DisableGrowthControl() { SetGrowthControlState(false); }
+  void SetGrowthControlState(bool state);
+  bool GrowthControlState();
 
   // Protect access to the heap.
   void WriteProtect(bool read_only);
@@ -274,6 +277,16 @@
 };
 #endif  // defined(DEBUG)
 
+
+class NoHeapGrowthControlScope : public StackResource {
+ public:
+  NoHeapGrowthControlScope();
+  ~NoHeapGrowthControlScope();
+ private:
+  bool current_growth_controller_state_;
+  DISALLOW_COPY_AND_ASSIGN(NoHeapGrowthControlScope);
+};
+
 }  // namespace dart
 
 #endif  // VM_HEAP_H_
diff --git a/runtime/vm/instructions_arm.cc b/runtime/vm/instructions_arm.cc
index a57545e..96cab68 100644
--- a/runtime/vm/instructions_arm.cc
+++ b/runtime/vm/instructions_arm.cc
@@ -16,14 +16,14 @@
     : end_(reinterpret_cast<uword*>(pc)),
       target_address_pool_index_(-1),
       args_desc_load_end_(-1),
-      args_desc_pool_index_(-1),
+      args_desc_(Array::Handle()),
       ic_data_load_end_(-1),
-      ic_data_pool_index_(-1),
+      ic_data_(ICData::Handle()),
       object_pool_(Array::Handle(code.ObjectPool())) {
   ASSERT(code.ContainsInstructionAt(pc));
   ASSERT(Back(1) == 0xe12fff3e);  // Last instruction: blx lr
   Register reg;
-  args_desc_load_end_ =
+  ic_data_load_end_ =
       DecodeLoadWordFromPool(1, &reg, &target_address_pool_index_);
   ASSERT(reg == LR);
 }
@@ -36,6 +36,48 @@
 
 
 // Decodes a load sequence ending at end. Returns the register being loaded and
+// the loaded object.
+// Returns the location of the load sequence, counting the number of
+// instructions back from the end of the call pattern.
+int CallPattern::DecodeLoadObject(int end, Register* reg, Object* obj) {
+  ASSERT(end > 0);
+  uword instr = Back(end + 1);
+  if ((instr & 0xfff00000) == 0xe5900000) {  // ldr reg, [reg, #+offset]
+    int index = 0;
+    end = DecodeLoadWordFromPool(end, reg, &index);
+    *obj = object_pool_.At(index);
+  } else {
+    int value = 0;
+    end = DecodeLoadWordImmediate(end, reg, &value);
+    *obj = reinterpret_cast<RawObject*>(value);
+  }
+  return end;
+}
+
+
+// Decodes a load sequence ending at end. Returns the register being loaded and
+// the loaded immediate value.
+// Returns the location of the load sequence, counting the number of
+// instructions back from the end of the call pattern.
+int CallPattern::DecodeLoadWordImmediate(int end, Register* reg, int* value) {
+  ASSERT(end > 0);
+  uword instr = Back(++end);
+  int imm = 0;
+  if ((instr & 0xfff00000) == 0xe3400000) {  // movt reg, #imm_hi
+    imm |= (instr & 0xf0000) << 12;
+    imm |= (instr & 0xfff) << 16;
+    instr = Back(++end);
+  }
+  ASSERT((instr & 0xfff00000) == 0xe3000000);  // movw reg, #imm_lo
+  imm |= (instr & 0xf0000) >> 4;
+  imm |= instr & 0xfff;
+  *reg = static_cast<Register>((instr & 0xf000) >> 12);
+  *value = imm;
+  return end;
+}
+
+
+// Decodes a load sequence ending at end. Returns the register being loaded and
 // the index in the pool being read from.
 // Returns the location of the load sequence, counting the number of
 // instructions back from the end of the call pattern.
@@ -57,17 +99,7 @@
       *reg = static_cast<Register>((instr & 0xf000) >> 12);
     } else {
       ASSERT((instr & 0xffff0000) == 0xe08a0000);  // add reg, pp, reg
-      instr = Back(++end);
-      if ((instr & 0xfff00000) == 0xe3400000) {  // movt reg, offset_hi
-        offset |= (instr & 0xf0000) << 12;
-        offset |= (instr & 0xfff) << 16;
-        instr = Back(++end);
-      }
-      ASSERT((instr & 0xfff00000) == 0xe3000000);  // movw reg, offset_lo
-      ASSERT((offset & 0xffff) == 0);
-      offset |= (instr & 0xf0000) >> 4;
-      offset |= instr & 0xfff;
-      *reg = static_cast<Register>((instr & 0xf000) >> 12);
+      end = DecodeLoadWordImmediate(end, reg, &offset);
     }
   }
   offset += kHeapObjectTag;
@@ -78,33 +110,23 @@
 
 
 RawICData* CallPattern::IcData() {
-  if (ic_data_pool_index_ < 0) {
+  if (ic_data_.IsNull()) {
     Register reg;
-    // Loading of the argument descriptor must be decoded first, if not already.
-    if (args_desc_pool_index_ < 0) {
-      ic_data_load_end_ = DecodeLoadWordFromPool(
-          args_desc_load_end_, &reg, &args_desc_pool_index_);
-      ASSERT(reg == R4);
-    }
-    DecodeLoadWordFromPool(ic_data_load_end_, &reg, &ic_data_pool_index_);
+    args_desc_load_end_ = DecodeLoadObject(ic_data_load_end_, &reg, &ic_data_);
     ASSERT(reg == R5);
   }
-  ICData& ic_data = ICData::Handle();
-  ic_data ^= object_pool_.At(ic_data_pool_index_);
-  return ic_data.raw();
+  return ic_data_.raw();
 }
 
 
 RawArray* CallPattern::ArgumentsDescriptor() {
-  if (args_desc_pool_index_ < 0) {
+  if (args_desc_.IsNull()) {
+    IcData();  // Loading of the ic_data must be decoded first, if not already.
     Register reg;
-    ic_data_load_end_ = DecodeLoadWordFromPool(
-        args_desc_load_end_, &reg, &args_desc_pool_index_);
+    DecodeLoadObject(args_desc_load_end_, &reg, &args_desc_);
     ASSERT(reg == R4);
   }
-  Array& args_desc = Array::Handle();
-  args_desc ^= object_pool_.At(args_desc_pool_index_);
-  return args_desc.raw();
+  return args_desc_.raw();
 }
 
 
diff --git a/runtime/vm/instructions_arm.h b/runtime/vm/instructions_arm.h
index 3995c69..0fb176d 100644
--- a/runtime/vm/instructions_arm.h
+++ b/runtime/vm/instructions_arm.h
@@ -27,13 +27,15 @@
 
  private:
   uword Back(int n) const;
+  int DecodeLoadObject(int end, Register* reg, Object* obj);
+  int DecodeLoadWordImmediate(int end, Register* reg, int* value);
   int DecodeLoadWordFromPool(int end, Register* reg, int* index);
   const uword* end_;
   int target_address_pool_index_;
   int args_desc_load_end_;
-  int args_desc_pool_index_;
+  Array& args_desc_;
   int ic_data_load_end_;
-  int ic_data_pool_index_;
+  ICData& ic_data_;
   const Array& object_pool_;
 
   DISALLOW_COPY_AND_ASSIGN(CallPattern);
diff --git a/runtime/vm/instructions_mips.cc b/runtime/vm/instructions_mips.cc
index 3bba216..bfc7f1d 100644
--- a/runtime/vm/instructions_mips.cc
+++ b/runtime/vm/instructions_mips.cc
@@ -13,8 +13,20 @@
 
 CallPattern::CallPattern(uword pc, const Code& code)
     : end_(reinterpret_cast<uword*>(pc)),
-      pool_index_(DecodePoolIndex()),
-      object_pool_(Array::Handle(code.ObjectPool())) { }
+      target_address_pool_index_(-1),
+      args_desc_load_end_(-1),
+      args_desc_pool_index_(-1),
+      ic_data_load_end_(-1),
+      ic_data_pool_index_(-1),
+      object_pool_(Array::Handle(code.ObjectPool())) {
+  ASSERT(code.ContainsInstructionAt(pc));
+  ASSERT(Back(2) == 0x0020f809);  // Last instruction: jalr RA, TMP(=R1)
+  Register reg;
+  // First end is 0 so that we begin from the delay slot of the jalr.
+  args_desc_load_end_ =
+     DecodeLoadWordFromPool(2, &reg, &target_address_pool_index_);
+  ASSERT(reg == TMP);
+}
 
 
 uword CallPattern::Back(int n) const {
@@ -23,15 +35,59 @@
 }
 
 
-int CallPattern::DecodePoolIndex() {
+int CallPattern::DecodeLoadWordFromPool(int end, Register* reg, int* index) {
+  ASSERT(end > 0);
+  uword i = Back(++end);
+  Instr* instr = Instr::At(reinterpret_cast<uword>(&i));
+  int offset = 0;
+  if ((instr->OpcodeField() == LW) && (instr->RsField() == PP)) {
+    offset = instr->SImmField();
+    *reg = instr->RtField();
+  } else {
+    ASSERT(instr->OpcodeField() == LW);
+    offset = instr->SImmField();
+    *reg = instr->RtField();
+
+    i = Back(++end);
+    instr = Instr::At(reinterpret_cast<uword>(&i));
+    ASSERT(instr->OpcodeField() == SPECIAL);
+    ASSERT(instr->FunctionField() == ADDU);
+    ASSERT(instr->RdField() == *reg);
+    ASSERT(instr->RsField() == *reg);
+    ASSERT(instr->RtField() == PP);
+
+    i = Back(++end);
+    instr = Instr::At(reinterpret_cast<uword>(&i));
+    ASSERT(instr->RtField() == *reg);
+    // Offset is signed, so add the upper 16 bits.
+    offset += (instr->UImmField() << 16);
+  }
+  offset += kHeapObjectTag;
+  ASSERT(Utils::IsAligned(offset, 4));
+  *index = (offset - Array::data_offset())/4;
+  return end;
+}
+
+
+RawICData* CallPattern::IcData() {
   UNIMPLEMENTED();
-  return 0;
+  return NULL;
+}
+
+
+RawArray* CallPattern::ArgumentsDescriptor() {
+  UNIMPLEMENTED();
+  return NULL;
 }
 
 
 uword CallPattern::TargetAddress() const {
-  UNIMPLEMENTED();
-  return 0;
+  ASSERT(target_address_pool_index_ >= 0);
+  const Object& target_address =
+      Object::Handle(object_pool_.At(target_address_pool_index_));
+  ASSERT(target_address.IsSmi());
+  // The address is stored in the object array as a RawSmi.
+  return reinterpret_cast<uword>(target_address.raw());
 }
 
 
diff --git a/runtime/vm/instructions_mips.h b/runtime/vm/instructions_mips.h
index 15c5cd3..1a71dc6 100644
--- a/runtime/vm/instructions_mips.h
+++ b/runtime/vm/instructions_mips.h
@@ -19,14 +19,21 @@
  public:
   CallPattern(uword pc, const Code& code);
 
+  RawICData* IcData();
+  RawArray* ArgumentsDescriptor();
+
   uword TargetAddress() const;
   void SetTargetAddress(uword target_address) const;
 
  private:
   uword Back(int n) const;
-  int DecodePoolIndex();
+  int DecodeLoadWordFromPool(int end, Register* reg, int* index);
   const uword* end_;
-  const int pool_index_;
+  int target_address_pool_index_;
+  int args_desc_load_end_;
+  int args_desc_pool_index_;
+  int ic_data_load_end_;
+  int ic_data_pool_index_;
   const Array& object_pool_;
 
   DISALLOW_COPY_AND_ASSIGN(CallPattern);
diff --git a/runtime/vm/instructions_mips_test.cc b/runtime/vm/instructions_mips_test.cc
index 3db5dae..cd3a226 100644
--- a/runtime/vm/instructions_mips_test.cc
+++ b/runtime/vm/instructions_mips_test.cc
@@ -15,12 +15,18 @@
 #define __ assembler->
 
 ASSEMBLER_TEST_GENERATE(Call, assembler) {
-  UNIMPLEMENTED();
+  __ BranchLinkPatchable(&StubCode::InstanceFunctionLookupLabel());
+  __ Ret();
 }
 
 
 ASSEMBLER_TEST_RUN(Call, test) {
-  CallPattern call(test->entry(), test->code());
+  // The return address, which must be the address of an instruction contained
+  // in the code, points to the Ret instruction above, i.e. two instructions
+  // before the end of the code buffer, including the delay slot for the
+  // return jump.
+  CallPattern call(test->entry() + test->code().Size() - (2*Instr::kInstrSize),
+                   test->code());
   EXPECT_EQ(StubCode::InstanceFunctionLookupLabel().address(),
             call.TargetAddress());
 }
diff --git a/runtime/vm/intermediate_language.cc b/runtime/vm/intermediate_language.cc
index 058b3ca..259419d 100644
--- a/runtime/vm/intermediate_language.cc
+++ b/runtime/vm/intermediate_language.cc
@@ -528,6 +528,11 @@
     while (next != NULL) {
       current = next;
       current->set_definition(other);
+      // Do not discard some useful inferred types.
+      // TODO(srdjan): Enable once checked mode issues investigated.
+      // if (current->Type() == this->Type()) {
+      //   current->SetReachingType(NULL);
+      // }
       next = current->next_use();
     }
 
@@ -1239,9 +1244,13 @@
   // Only handle strict-compares.
   if (comparison()->IsStrictCompare()) {
     Definition* replacement = comparison()->Canonicalize(optimizer);
-    if (replacement == comparison() || replacement == NULL) return this;
+    if ((replacement == comparison()) || (replacement == NULL)) {
+      return this;
+    }
     ComparisonInstr* comp = replacement->AsComparison();
-    if ((comp == NULL) || comp->CanDeoptimize()) return this;
+    if ((comp == NULL) || comp->CanDeoptimize()) {
+      return this;
+    }
 
     // Check that comparison is not serving as a pending deoptimization target
     // for conversions.
@@ -1274,7 +1283,9 @@
 
 
 Definition* StrictCompareInstr::Canonicalize(FlowGraphOptimizer* optimizer) {
-  if (!right()->BindsToConstant()) return this;
+  if (!right()->BindsToConstant()) {
+    return this;
+  }
   const Object& right_constant = right()->BoundConstant();
   Definition* left_defn = left()->definition();
   // TODO(fschneider): Handle other cases: e === false and e !== true/false.
@@ -1285,6 +1296,18 @@
     // Return left subexpression as the replacement for this instruction.
     return left_defn;
   }
+  // x = (a === b);  y = x !== true; -> y = a !== b.
+  // In order to merge two strict comares, 'left_strict' must have only one use.
+  // Do not check left's cid as it is required to be a strict compare.
+  StrictCompareInstr* left_strict = left_defn->AsStrictCompare();
+  if ((kind() == Token::kNE_STRICT) &&
+      (right_constant.raw() == Bool::True().raw()) &&
+      (left_strict != NULL) &&
+      (left_strict->HasOnlyUse(left()))) {
+    left_strict->set_kind(Token::NegateComparison(left_strict->kind()));
+    return left_strict;
+  }
+
   return this;
 }
 
@@ -1963,15 +1986,10 @@
 
 void LoadIndexedInstr::InferRange() {
   switch (class_id()) {
-    case kInt8ArrayCid:
     case kTypedDataInt8ArrayCid:
       range_ = new Range(RangeBoundary::FromConstant(-128),
                          RangeBoundary::FromConstant(127));
       break;
-    case kUint8ArrayCid:
-    case kUint8ClampedArrayCid:
-    case kExternalUint8ArrayCid:
-    case kExternalUint8ClampedArrayCid:
     case kTypedDataUint8ArrayCid:
     case kTypedDataUint8ClampedArrayCid:
     case kExternalTypedDataUint8ArrayCid:
@@ -1979,12 +1997,10 @@
       range_ = new Range(RangeBoundary::FromConstant(0),
                          RangeBoundary::FromConstant(255));
       break;
-    case kInt16ArrayCid:
     case kTypedDataInt16ArrayCid:
       range_ = new Range(RangeBoundary::FromConstant(-32768),
                          RangeBoundary::FromConstant(32767));
       break;
-    case kUint16ArrayCid:
     case kTypedDataUint16ArrayCid:
       range_ = new Range(RangeBoundary::FromConstant(0),
                          RangeBoundary::FromConstant(65535));
@@ -2234,20 +2250,6 @@
     case kArrayCid:
     case kImmutableArrayCid:
       return Array::length_offset();
-    case kInt8ArrayCid:
-    case kUint8ArrayCid:
-    case kUint8ClampedArrayCid:
-    case kInt16ArrayCid:
-    case kUint16ArrayCid:
-    case kInt32ArrayCid:
-    case kUint32ArrayCid:
-    case kInt64ArrayCid:
-    case kUint64ArrayCid:
-    case kFloat64ArrayCid:
-    case kFloat32ArrayCid:
-    case kExternalUint8ArrayCid:
-    case kExternalUint8ClampedArrayCid:
-      return ByteArray::length_offset();
     default:
       UNREACHABLE();
       return -1;
diff --git a/runtime/vm/intermediate_language.h b/runtime/vm/intermediate_language.h
index d11cc84..e489a26 100644
--- a/runtime/vm/intermediate_language.h
+++ b/runtime/vm/intermediate_language.h
@@ -57,16 +57,16 @@
   V(_GrowableObjectArray, get:length, GrowableArrayLength, 725548050)          \
   V(_GrowableObjectArray, get:_capacity, GrowableArrayCapacity, 725548050)     \
   V(_StringBase, get:length, StringBaseLength, 320803993)                      \
-  V(_StringBase, get:isEmpty, StringBaseIsEmpty, 711547329)                    \
+  V(_StringBase, get:isEmpty, StringBaseIsEmpty, 110632481)                    \
   V(_StringBase, codeUnitAt, StringBaseCodeUnitAt, 984449525)                  \
   V(_StringBase, [], StringBaseCharAt, 1062366987)                             \
-  V(_IntegerImplementation, toDouble, IntegerToDouble, 733149324)              \
+  V(_IntegerImplementation, toDouble, IntegerToDouble, 927078825)              \
   V(_Double, toInt, DoubleToInteger, 362666636)                                \
   V(_Double, truncateToDouble, DoubleTruncate, 620870996)                      \
   V(_Double, roundToDouble, DoubleRound, 620870996)                            \
   V(_Double, floorToDouble, DoubleFloor, 620870996)                            \
   V(_Double, ceilToDouble, DoubleCeil, 620870996)                              \
-  V(_Double, pow, DoublePow, 1131958048)                                       \
+  V(_Double, pow, DoublePow, 1229411686)                                       \
   V(_Double, _modulo, DoubleMod, 437099337)                                    \
   V(::, sqrt, MathSqrt, 1662640002)                                            \
 
@@ -2421,7 +2421,7 @@
   virtual void EmitBranchCode(FlowGraphCompiler* compiler,
                               BranchInstr* branch) = 0;
 
- private:
+ protected:
   Token::Kind kind_;
 };
 
@@ -2499,6 +2499,7 @@
 
   bool needs_number_check() const { return needs_number_check_; }
   void set_needs_number_check(bool value) { needs_number_check_ = value; }
+  void set_kind(Token::Kind value) { kind_ = value; }
 
  private:
   // True if the comparison must check for double, Mint or Bigint and
diff --git a/runtime/vm/intermediate_language_x64.cc b/runtime/vm/intermediate_language_x64.cc
index afac01f..cc87b81 100644
--- a/runtime/vm/intermediate_language_x64.cc
+++ b/runtime/vm/intermediate_language_x64.cc
@@ -1136,7 +1136,7 @@
       __ SmiTag(result);
       break;
     case kTypedDataInt32ArrayCid:
-      __ movsxl(result, element_address);
+      __ movsxd(result, element_address);
       __ SmiTag(result);
       break;
     case kTypedDataUint32ArrayCid:
@@ -2328,13 +2328,40 @@
       break;
     }
     case Token::kTRUNCDIV: {
+      Label not_32bit, done;
+
+      Register temp = locs()->temp(0).reg();
+      ASSERT(left == RAX);
+      ASSERT((right != RDX) && (right != RAX));
+      ASSERT(temp == RDX);
+      ASSERT(result == RAX);
+
       // Handle divide by zero in runtime.
       __ testq(right, right);
       __ j(ZERO, deopt);
-      ASSERT(left == RAX);
-      ASSERT((right != RDX) && (right != RAX));
-      ASSERT(locs()->temp(0).reg() == RDX);
-      ASSERT(result == RAX);
+
+      // Check if both operands fit into 32bits as idiv with 64bit operands
+      // requires twice as many cycles and has much higher latency.
+      // We are checking this before untagging them to avoid corner case
+      // dividing INT_MAX by -1 that raises exception because quotient is
+      // too large for 32bit register.
+      __ movsxd(temp, left);
+      __ cmpq(temp, left);
+      __ j(NOT_EQUAL, &not_32bit);
+      __ movsxd(temp, right);
+      __ cmpq(temp, right);
+      __ j(NOT_EQUAL, &not_32bit);
+
+      // Both operands are 31bit smis. Divide using 32bit idiv.
+      __ SmiUntag(left);
+      __ SmiUntag(right);
+      __ cdq();
+      __ idivl(right);
+      __ movsxd(result, result);
+      __ jmp(&done);
+
+      // Divide using 64bit idiv.
+      __ Bind(&not_32bit);
       __ SmiUntag(left);
       __ SmiUntag(right);
       __ cqo();  // Sign extend RAX -> RDX:RAX.
@@ -2343,6 +2370,7 @@
       // case we cannot tag the result.
       __ cmpq(result, Immediate(0x4000000000000000));
       __ j(EQUAL, deopt);
+      __ Bind(&done);
       __ SmiTag(result);
       break;
     }
diff --git a/runtime/vm/intrinsifier.cc b/runtime/vm/intrinsifier.cc
index 1908db6..f7303a9 100644
--- a/runtime/vm/intrinsifier.cc
+++ b/runtime/vm/intrinsifier.cc
@@ -123,10 +123,6 @@
   lib = Library::MathLibrary();
   MATH_LIB_INTRINSIC_LIST(SETUP_FUNCTION);
 
-  // Set up all scalar list lib functions that can be intrisified.
-  lib = Library::ScalarlistLibrary();
-  SCALARLIST_LIB_INTRINSIC_LIST(SETUP_FUNCTION);
-
   // Set up all dart:typeddata lib functions that can be intrisified.
   lib = Library::TypedDataLibrary();
   TYPEDDATA_LIB_INTRINSIC_LIST(SETUP_FUNCTION);
@@ -155,8 +151,6 @@
     CORE_LIB_INTRINSIC_LIST(FIND_INTRINSICS);
   } else if (lib.raw() == Library::TypedDataLibrary()) {
     TYPEDDATA_LIB_INTRINSIC_LIST(FIND_INTRINSICS);
-  } else if (lib.raw() == Library::ScalarlistLibrary()) {
-    SCALARLIST_LIB_INTRINSIC_LIST(FIND_INTRINSICS);
   } else if (lib.raw() == Library::MathLibrary()) {
     MATH_LIB_INTRINSIC_LIST(FIND_INTRINSICS);
   }
diff --git a/runtime/vm/intrinsifier.h b/runtime/vm/intrinsifier.h
index 5c0aee9..f57a929 100644
--- a/runtime/vm/intrinsifier.h
+++ b/runtime/vm/intrinsifier.h
@@ -17,47 +17,47 @@
 // build and run to get the correct fingerprint from the mismatch error.
 #define CORE_LIB_INTRINSIC_LIST(V)                                             \
   V(_IntegerImplementation, _addFromInteger, Integer_addFromInteger, 726019207)\
-  V(_IntegerImplementation, +, Integer_add, 959303888)                         \
+  V(_IntegerImplementation, +, Integer_add, 25837296)                          \
   V(_IntegerImplementation, _subFromInteger, Integer_subFromInteger, 726019207)\
-  V(_IntegerImplementation, -, Integer_sub, 483122878)                         \
+  V(_IntegerImplementation, -, Integer_sub, 1697139934)                        \
   V(_IntegerImplementation, _mulFromInteger, Integer_mulFromInteger, 726019207)\
-  V(_IntegerImplementation, *, Integer_mul, 1043837343)                        \
-  V(_IntegerImplementation, %, Integer_modulo, 2027609817)                     \
-  V(_IntegerImplementation, ~/, Integer_truncDivide, 958840900)                \
-  V(_IntegerImplementation, unary-, Integer_negate, 678480358)                 \
+  V(_IntegerImplementation, *, Integer_mul, 110370751)                         \
+  V(_IntegerImplementation, %, Integer_modulo, 108639519)                      \
+  V(_IntegerImplementation, ~/, Integer_truncDivide, 1187354250)               \
+  V(_IntegerImplementation, unary-, Integer_negate, 675709702)                 \
   V(_IntegerImplementation, _bitAndFromInteger,                                \
     Integer_bitAndFromInteger, 726019207)                                      \
-  V(_IntegerImplementation, &, Integer_bitAnd, 1692486097)                     \
+  V(_IntegerImplementation, &, Integer_bitAnd, 759019505)                      \
   V(_IntegerImplementation, _bitOrFromInteger,                                 \
     Integer_bitOrFromInteger, 726019207)                                       \
-  V(_IntegerImplementation, |, Integer_bitOr, 66350242)                        \
+  V(_IntegerImplementation, |, Integer_bitOr, 1280367298)                      \
   V(_IntegerImplementation, _bitXorFromInteger,                                \
     Integer_bitXorFromInteger, 726019207)                                      \
-  V(_IntegerImplementation, ^, Integer_bitXor, 1620294403)                     \
+  V(_IntegerImplementation, ^, Integer_bitXor, 686827811)                      \
   V(_IntegerImplementation,                                                    \
     _greaterThanFromInteger,                                                   \
     Integer_greaterThanFromInt, 79222670)                                      \
-  V(_IntegerImplementation, >, Integer_greaterThan, 1800453857)                \
-  V(_IntegerImplementation, ==, Integer_equal, 1540405784)                     \
+  V(_IntegerImplementation, >, Integer_greaterThan, 866987265)                 \
+  V(_IntegerImplementation, ==, Integer_equal, 408178104)                      \
   V(_IntegerImplementation, _equalToInteger, Integer_equalToInteger, 79222670) \
-  V(_IntegerImplementation, <, Integer_lessThan, 1426685575)                   \
-  V(_IntegerImplementation, <=, Integer_lessEqualThan, 1065121761)             \
-  V(_IntegerImplementation, >=, Integer_greaterEqualThan, 1065151552)          \
-  V(_IntegerImplementation, <<, Integer_shl, 386573125)                        \
-  V(_IntegerImplementation, >>, Integer_sar, 1170883039)                       \
+  V(_IntegerImplementation, <, Integer_lessThan, 1423914919)                   \
+  V(_IntegerImplementation, <=, Integer_lessEqualThan, 890963352)              \
+  V(_IntegerImplementation, >=, Integer_greaterEqualThan, 890993143)           \
+  V(_IntegerImplementation, <<, Integer_shl, 1600590181)                       \
+  V(_IntegerImplementation, >>, Integer_sar, 237416447)                        \
   V(_Smi, ~, Smi_bitNegate, 882629793)                                         \
-  V(_Double, >, Double_greaterThan, 2056391997)                                \
-  V(_Double, >=, Double_greaterEqualThan, 1300634558)                          \
-  V(_Double, <, Double_lessThan, 1598098437)                                   \
-  V(_Double, <=, Double_lessEqualThan, 1300604767)                             \
-  V(_Double, ==, Double_equal, 1206706717)                                     \
-  V(_Double, +, Double_add, 1965033293)                                        \
-  V(_Double, -, Double_sub, 1212327731)                                        \
-  V(_Double, *, Double_mul, 395243827)                                         \
-  V(_Double, /, Double_div, 809804402)                                         \
+  V(_Double, >, Double_greaterThan, 498448864)                                 \
+  V(_Double, >=, Double_greaterEqualThan, 1126476149)                          \
+  V(_Double, <, Double_lessThan, 1595327781)                                   \
+  V(_Double, <=, Double_lessEqualThan, 1126446358)                             \
+  V(_Double, ==, Double_equal, 48480576)                                       \
+  V(_Double, +, Double_add, 407090160)                                         \
+  V(_Double, -, Double_sub, 1801868246)                                        \
+  V(_Double, *, Double_mul, 984784342)                                         \
+  V(_Double, /, Double_div, 1399344917)                                        \
   V(_Double, get:isNaN, Double_getIsNaN, 54462366)                             \
   V(_Double, get:isNegative, Double_getIsNegative, 54462366)                   \
-  V(_Double, _mulFromInteger, Double_mulFromInteger, 815838159)                \
+  V(_Double, _mulFromInteger, Double_mulFromInteger, 353781714)                \
   V(_Double, .fromInteger, Double_fromInteger, 842078193)                      \
   V(_Double, toInt, Double_toInt, 362666636)                                   \
   V(_ObjectArray, ., ObjectArray_Allocate, 97987288)                           \
@@ -71,12 +71,12 @@
   V(_GrowableObjectArray, []=, GrowableArray_setIndexed, 1048007636)           \
   V(_GrowableObjectArray, _setLength, GrowableArray_setLength, 796709584)      \
   V(_GrowableObjectArray, _setData, GrowableArray_setData, 629110947)          \
-  V(_GrowableObjectArray, add, GrowableArray_add, 1367698386)                  \
+  V(_GrowableObjectArray, add, GrowableArray_add, 2139340847)                  \
   V(_ImmutableArray, [], ImmutableArray_getIndexed, 486821199)                 \
   V(_ImmutableArray, get:length, ImmutableArray_getLength, 433698233)          \
-  V(Object, ==, Object_equal, 2126956595)                                      \
+  V(Object, ==, Object_equal, 2126867222)                                      \
   V(_StringBase, get:hashCode, String_getHashCode, 320803993)                  \
-  V(_StringBase, get:isEmpty, String_getIsEmpty, 711547329)                    \
+  V(_StringBase, get:isEmpty, String_getIsEmpty, 110632481)                    \
   V(_StringBase, get:length, String_getLength, 320803993)                      \
   V(_StringBase, codeUnitAt, String_codeUnitAt, 984449525)                     \
   V(_OneByteString, get:hashCode, OneByteString_getHashCode, 682660413)        \
@@ -88,35 +88,6 @@
   V(::, cos, Math_cos, 1749547468)                                             \
 
 
-// Note that any intrinsified function is not inlined. Some optimizations
-// rely on seeing the factories below instead of their inlined code.
-#define SCALARLIST_LIB_INTRINSIC_LIST(V)                                       \
-  V(_ByteArrayBase, get:length, ByteArrayBase_getLength, 1098081765)           \
-  V(_Int64Array, [], Int64Array_getIndexed, 504894128)                         \
-  V(_Uint64Array, [], Uint64Array_getIndexed, 31272531)                        \
-  V(_Int8Array, _new, Int8Array_new, 535958453)                                \
-  V(_Uint8Array, _new, Uint8Array_new, 604355565)                              \
-  V(_Uint8ClampedArray, _new, Uint8ClampedArray_new, 1070949952)               \
-  V(_Int16Array, _new, Int16Array_new, 903723993)                              \
-  V(_Uint16Array, _new, Uint16Array_new, 133542762)                            \
-  V(_Int32Array, _new, Int32Array_new, 8218286)                                \
-  V(_Uint32Array, _new, Uint32Array_new, 469402161)                            \
-  V(_Int64Array, _new, Int64Array_new, 60605075)                               \
-  V(_Uint64Array, _new, Uint64Array_new, 624354107)                            \
-  V(_Float32Array, _new, Float32Array_new, 109944959)                          \
-  V(_Float64Array, _new, Float64Array_new, 147668392)                          \
-  V(Int8List, ., Int8Array_factory, 817410959)                                 \
-  V(Uint8List, ., Uint8Array_factory, 220896178)                               \
-  V(Uint8ClampedList, ., Uint8ClampedArray_factory, 422034060)                 \
-  V(Int16List, ., Int16Array_factory, 214246025)                               \
-  V(Uint16List, ., Uint16Array_factory, 137929963)                             \
-  V(Int32List, ., Int32Array_factory, 1977571010)                              \
-  V(Uint32List, ., Uint32Array_factory, 407638944)                             \
-  V(Int64List, ., Int64Array_factory, 885130273)                               \
-  V(Uint64List, ., Uint64Array_factory, 1471017221)                            \
-  V(Float32List, ., Float32Array_factory, 2035252095)                          \
-  V(Float64List, ., Float64Array_factory, 1037441059)                          \
-
 #define TYPEDDATA_LIB_INTRINSIC_LIST(V)                                        \
   V(_TypedList, get:length, TypedData_getLength, 231908172)                    \
   V(_Int8Array, _new, TypedData_Int8Array_new, 844274443)                      \
@@ -130,17 +101,19 @@
   V(_Uint64Array, _new, TypedData_Uint64Array_new, 977566635)                  \
   V(_Float32Array, _new, TypedData_Float32Array_new, 1053133615)               \
   V(_Float64Array, _new, TypedData_Float64Array_new, 936673303)                \
-  V(_Int8Array, ., TypedData_Int8Array_factory, 1852699666)                    \
-  V(_Uint8Array, ., TypedData_Uint8Array_factory, 1014667000)                  \
-  V(_Uint8ClampedArray, ., TypedData_Uint8ClampedArray_factory, 519376744)     \
-  V(_Int16Array, ., TypedData_Int16Array_factory, 1069515268)                  \
-  V(_Uint16Array, ., TypedData_Uint16Array_factory, 1892182763)                \
-  V(_Int32Array, ., TypedData_Int32Array_factory, 1724127394)                  \
-  V(_Uint32Array, ., TypedData_Uint32Array_factory, 1251657079)                \
-  V(_Int64Array, ., TypedData_Int64Array_factory, 1922050636)                  \
-  V(_Uint64Array, ., TypedData_Uint64Array_factory, 1279581075)                \
-  V(_Float32Array, ., TypedData_Float32Array_factory, 112704438)               \
-  V(_Float64Array, ., TypedData_Float64Array_factory, 41426340)                \
+  V(_Float32x4Array, _new, TypedData_Float32x4Array_new, 212088644)            \
+  V(_Int8Array, ., TypedData_Int8Array_factory, 632939448)                     \
+  V(_Uint8Array, ., TypedData_Uint8Array_factory, 1942390430)                  \
+  V(_Uint8ClampedArray, ., TypedData_Uint8ClampedArray_factory, 1447100174)    \
+  V(_Int16Array, ., TypedData_Int16Array_factory, 1997238698)                  \
+  V(_Uint16Array, ., TypedData_Uint16Array_factory, 672422545)                 \
+  V(_Int32Array, ., TypedData_Int32Array_factory, 504367176)                   \
+  V(_Uint32Array, ., TypedData_Uint32Array_factory, 31896861)                  \
+  V(_Int64Array, ., TypedData_Int64Array_factory, 702290418)                   \
+  V(_Uint64Array, ., TypedData_Uint64Array_factory, 59820857)                  \
+  V(_Float32Array, ., TypedData_Float32Array_factory, 1040427868)              \
+  V(_Float64Array, ., TypedData_Float64Array_factory, 969149770)               \
+  V(_Float32x4Array, ., TypedData_Float32x4Array_factory, 175242544)           \
 
 // TODO(srdjan): Implement _FixedSizeArrayIterator, get:current and
 //   _FixedSizeArrayIterator, moveNext.
@@ -164,7 +137,6 @@
 
   CORE_LIB_INTRINSIC_LIST(DECLARE_FUNCTION)
   MATH_LIB_INTRINSIC_LIST(DECLARE_FUNCTION)
-  SCALARLIST_LIB_INTRINSIC_LIST(DECLARE_FUNCTION)
   TYPEDDATA_LIB_INTRINSIC_LIST(DECLARE_FUNCTION)
 
 #undef DECLARE_FUNCTION
diff --git a/runtime/vm/intrinsifier_arm.cc b/runtime/vm/intrinsifier_arm.cc
index a1b756e..1f86747 100644
--- a/runtime/vm/intrinsifier_arm.cc
+++ b/runtime/vm/intrinsifier_arm.cc
@@ -80,131 +80,6 @@
 }
 
 
-bool Intrinsifier::ByteArrayBase_getLength(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int8Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int8Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint8Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint8Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint8ClampedArray_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint8ClampedArray_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int16Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int16Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint16Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint16Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int32Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int32Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint32Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint32Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int64Array_getIndexed(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int64Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int64Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint64Array_getIndexed(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint64Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint64Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Float32Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Float32Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Float64Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Float64Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
 bool Intrinsifier::TypedData_getLength(Assembler* assembler) {
   return true;
 }
diff --git a/runtime/vm/intrinsifier_ia32.cc b/runtime/vm/intrinsifier_ia32.cc
index db68d84..f5a2eb9 100644
--- a/runtime/vm/intrinsifier_ia32.cc
+++ b/runtime/vm/intrinsifier_ia32.cc
@@ -458,15 +458,6 @@
 }
 
 
-// Gets the length of a ByteArray.
-bool Intrinsifier::ByteArrayBase_getLength(Assembler* assembler) {
-  __ movl(EAX, Address(ESP, + 1 * kWordSize));
-  __ movl(EAX, FieldAddress(EAX, ByteArray::length_offset()));
-  __ ret();
-  return true;
-}
-
-
 #define TYPED_ARRAY_ALLOCATION(type_name, cid, max_len, scale_factor)          \
   Label fall_through;                                                          \
   const intptr_t kArrayLengthStackOffset = 1 * kWordSize;                      \
@@ -482,6 +473,13 @@
   /* EDI: untagged array length. */                                            \
   __ cmpl(EDI, Immediate(max_len));                                            \
   __ j(GREATER, &fall_through);                                                \
+  /* Special case for scaling by 16. */                                        \
+  if (scale_factor == TIMES_16) {                                              \
+    /* double length of array. */                                              \
+    __ addl(EDI, EDI);                                                         \
+    /* only scale by 8. */                                                     \
+    scale_factor = TIMES_8;                                                    \
+  }                                                                            \
   const intptr_t fixed_size = sizeof(Raw##type_name) + kObjectAlignment - 1;   \
   __ leal(EDI, Address(EDI, scale_factor, fixed_size));                        \
   __ andl(EDI, Immediate(-kObjectAlignment));                                  \
@@ -553,39 +551,6 @@
   __ Bind(&fall_through);                                                      \
 
 
-#define SCALARLIST_ALLOCATOR(clazz, scale)                                     \
-bool Intrinsifier::clazz##_new(Assembler* assembler) {                         \
-  TYPED_ARRAY_ALLOCATION(clazz, k##clazz##Cid, clazz::kMaxElements, scale);    \
-  return false;                                                                \
-}                                                                              \
-bool Intrinsifier::clazz##_factory(Assembler* assembler) {                     \
-  TYPED_ARRAY_ALLOCATION(clazz, k##clazz##Cid, clazz::kMaxElements, scale);    \
-  return false;                                                                \
-}
-
-
-SCALARLIST_ALLOCATOR(Int8Array, TIMES_1)
-SCALARLIST_ALLOCATOR(Uint8Array, TIMES_1)
-SCALARLIST_ALLOCATOR(Uint8ClampedArray, TIMES_1)
-SCALARLIST_ALLOCATOR(Int16Array, TIMES_2)
-SCALARLIST_ALLOCATOR(Uint16Array, TIMES_2)
-SCALARLIST_ALLOCATOR(Int32Array, TIMES_4)
-SCALARLIST_ALLOCATOR(Uint32Array, TIMES_4)
-SCALARLIST_ALLOCATOR(Int64Array, TIMES_8)
-SCALARLIST_ALLOCATOR(Uint64Array, TIMES_8)
-SCALARLIST_ALLOCATOR(Float32Array, TIMES_4)
-SCALARLIST_ALLOCATOR(Float64Array, TIMES_8)
-
-
-bool Intrinsifier::Int64Array_getIndexed(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint64Array_getIndexed(Assembler* assembler) {
-  return false;
-}
-
 
 // Gets the length of a TypedData.
 bool Intrinsifier::TypedData_getLength(Assembler* assembler) {
@@ -602,6 +567,7 @@
     case 2: return TIMES_2;
     case 4: return TIMES_4;
     case 8: return TIMES_8;
+    case 16: return TIMES_16;
   }
   UNREACHABLE();
   return static_cast<ScaleFactor>(0);
diff --git a/runtime/vm/intrinsifier_mips.cc b/runtime/vm/intrinsifier_mips.cc
index cfe0b82..a93d678 100644
--- a/runtime/vm/intrinsifier_mips.cc
+++ b/runtime/vm/intrinsifier_mips.cc
@@ -80,131 +80,6 @@
 }
 
 
-bool Intrinsifier::ByteArrayBase_getLength(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int8Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int8Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint8Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint8Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint8ClampedArray_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint8ClampedArray_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int16Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int16Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint16Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint16Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int32Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int32Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint32Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint32Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int64Array_getIndexed(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int64Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Int64Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint64Array_getIndexed(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint64Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Uint64Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Float32Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Float32Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Float64Array_new(Assembler* assembler) {
-  return false;
-}
-
-
-bool Intrinsifier::Float64Array_factory(Assembler* assembler) {
-  return false;
-}
-
-
 bool Intrinsifier::TypedData_getLength(Assembler* assembler) {
   return true;
 }
diff --git a/runtime/vm/intrinsifier_x64.cc b/runtime/vm/intrinsifier_x64.cc
index 3119fdb..16b08a7 100644
--- a/runtime/vm/intrinsifier_x64.cc
+++ b/runtime/vm/intrinsifier_x64.cc
@@ -411,17 +411,6 @@
 }
 
 
-bool Intrinsifier::ByteArrayBase_getLength(Assembler* assembler) {
-  __ movq(RAX, Address(RSP, + 1 * kWordSize));
-  __ movq(RAX, FieldAddress(RAX, ByteArray::length_offset()));
-  __ ret();
-  // Generate enough code to satisfy patchability constraint.
-  intptr_t offset = __ CodeSize();
-  __ nop(JumpPattern::InstructionLength() - offset);
-  return true;
-}
-
-
 
 // Tests if index is a valid length (Smi and within valid index range),
 // jumps to fall_through if it is not.
@@ -454,6 +443,13 @@
   /* RDI: untagged array length. */                                            \
   __ cmpq(RDI, Immediate(max_len));                                            \
   __ j(GREATER, &fall_through);                                                \
+  /* Special case for scaling by 16. */                                        \
+  if (scale_factor == TIMES_16) {                                              \
+    /* double length of array. */                                              \
+    __ addq(RDI, RDI);                                                         \
+    /* only scale by 8. */                                                     \
+    scale_factor = TIMES_8;                                                    \
+  }                                                                            \
   const intptr_t fixed_size = sizeof(Raw##type_name) + kObjectAlignment - 1;   \
   __ leaq(RDI, Address(RDI, scale_factor, fixed_size));                        \
   __ andq(RDI, Immediate(-kObjectAlignment));                                  \
@@ -530,75 +526,6 @@
   __ Bind(&fall_through);                                                      \
 
 
-#define SCALARLIST_ALLOCATOR(clazz, scale)                                     \
-bool Intrinsifier::clazz##_new(Assembler* assembler) {                         \
-  TYPED_ARRAY_ALLOCATION(clazz, k##clazz##Cid, clazz::kMaxElements, scale);    \
-  return false;                                                                \
-}                                                                              \
-bool Intrinsifier::clazz##_factory(Assembler* assembler) {                     \
-  TYPED_ARRAY_ALLOCATION(clazz, k##clazz##Cid, clazz::kMaxElements, scale);    \
-  return false;                                                                \
-}
-
-
-SCALARLIST_ALLOCATOR(Int8Array, TIMES_1)
-SCALARLIST_ALLOCATOR(Uint8Array, TIMES_1)
-SCALARLIST_ALLOCATOR(Uint8ClampedArray, TIMES_1)
-SCALARLIST_ALLOCATOR(Int16Array, TIMES_2)
-SCALARLIST_ALLOCATOR(Uint16Array, TIMES_2)
-SCALARLIST_ALLOCATOR(Int32Array, TIMES_4)
-SCALARLIST_ALLOCATOR(Uint32Array, TIMES_4)
-SCALARLIST_ALLOCATOR(Int64Array, TIMES_8)
-SCALARLIST_ALLOCATOR(Uint64Array, TIMES_8)
-SCALARLIST_ALLOCATOR(Float32Array, TIMES_4)
-SCALARLIST_ALLOCATOR(Float64Array, TIMES_8)
-
-
-bool Intrinsifier::Int64Array_getIndexed(Assembler* assembler) {
-  Label fall_through;
-  TestByteArrayGetIndex(assembler, &fall_through);
-  // R12: index as Smi.
-  // RAX: array.
-  __ movq(RAX, FieldAddress(RAX,
-                            R12,
-                            TIMES_4,
-                            Int64Array::data_offset()));
-  // Copy RAX into R12.
-  // We destroy R12 while testing if RAX can fit inside a Smi.
-  __ movq(R12, RAX);
-  // Verify that the signed value in RAX can fit inside a Smi.
-  __ shlq(R12, Immediate(0x1));
-  // Jump to fall_through if it can not.
-  __ j(OVERFLOW, &fall_through, Assembler::kNearJump);
-  __ SmiTag(RAX);
-  __ ret();
-  __ Bind(&fall_through);
-  return false;
-}
-
-
-bool Intrinsifier::Uint64Array_getIndexed(Assembler* assembler) {
-  Label fall_through;
-  TestByteArrayGetIndex(assembler, &fall_through);
-  // R12: index as Smi.
-  // RAX: array.
-  __ movq(RAX, FieldAddress(RAX,
-                            R12,
-                            TIMES_4,
-                            Uint64Array::data_offset()));
-  // Copy RAX into R12.
-  // We destroy R12 while testing if RAX can fit inside a Smi.
-  __ movq(R12, RAX);
-  // Verify that the unsigned value in RAX can be stored in a Smi.
-  __ shrq(R12, Immediate(kSmiBits));
-  __ j(NOT_ZERO, &fall_through, Assembler::kNearJump);  // Won't fit Smi.
-  __ SmiTag(RAX);
-  __ ret();
-  __ Bind(&fall_through);
-  return false;
-}
-
-
 // Gets the length of a TypedData.
 bool Intrinsifier::TypedData_getLength(Assembler* assembler) {
   __ movq(RAX, Address(RSP, + 1 * kWordSize));
@@ -617,6 +544,7 @@
     case 2: return TIMES_2;
     case 4: return TIMES_4;
     case 8: return TIMES_8;
+    case 16: return TIMES_16;
   }
   UNREACHABLE();
   return static_cast<ScaleFactor>(0);
@@ -721,7 +649,7 @@
 
 
 bool Intrinsifier::Integer_modulo(Assembler* assembler) {
-  Label fall_through, return_zero, try_modulo;
+  Label fall_through, return_zero, try_modulo, not_32bit;
   TestBothArgumentsSmis(assembler, &fall_through);
   // RAX: right argument (divisor)
   // Check if modulo by zero -> exception thrown in main function.
@@ -735,35 +663,84 @@
   __ j(GREATER, &try_modulo, Assembler::kNearJump);
   __ movq(RAX, RCX);  // Return dividend as it is smaller than divisor.
   __ ret();
+
   __ Bind(&return_zero);
   __ xorq(RAX, RAX);  // Return zero.
   __ ret();
+
   __ Bind(&try_modulo);
   // RAX: right (non-null divisor).
   __ movq(RCX, RAX);
-  __ SmiUntag(RCX);
   __ movq(RAX, Address(RSP, + 2 * kWordSize));  // Left argument (dividend).
+
+  // Check if both operands fit into 32bits as idiv with 64bit operands
+  // requires twice as many cycles and has much higher latency. We are checking
+  // this before untagging them to avoid corner case dividing INT_MAX by -1 that
+  // raises exception because quotient is too large for 32bit register.
+  __ movsxd(RBX, RAX);
+  __ cmpq(RBX, RAX);
+  __ j(NOT_EQUAL, &not_32bit);
+  __ movsxd(RBX, RCX);
+  __ cmpq(RBX, RCX);
+  __ j(NOT_EQUAL, &not_32bit);
+
+  // Both operands are 31bit smis. Divide using 32bit idiv.
   __ SmiUntag(RAX);
+  __ SmiUntag(RCX);
+  __ cdq();
+  __ idivl(RCX);
+  __ movsxd(RAX, RDX);
+  __ SmiTag(RAX);
+  __ ret();
+
+  // Divide using 64bit idiv.
+  __ Bind(&not_32bit);
+  __ SmiUntag(RAX);
+  __ SmiUntag(RCX);
   __ cqo();
   __ idivq(RCX);
   __ movq(RAX, RDX);
   __ SmiTag(RAX);
   __ ret();
+
   __ Bind(&fall_through);
   return false;
 }
 
 
 bool Intrinsifier::Integer_truncDivide(Assembler* assembler) {
-  Label fall_through;
+  Label fall_through, not_32bit;
   TestBothArgumentsSmis(assembler, &fall_through);
   // RAX: right argument (divisor)
   __ cmpq(RAX, Immediate(0));
   __ j(EQUAL, &fall_through, Assembler::kNearJump);
   __ movq(RCX, RAX);
-  __ SmiUntag(RCX);
   __ movq(RAX, Address(RSP, + 2 * kWordSize));  // Left argument (dividend).
+
+  // Check if both operands fit into 32bits as idiv with 64bit operands
+  // requires twice as many cycles and has much higher latency. We are checking
+  // this before untagging them to avoid corner case dividing INT_MAX by -1 that
+  // raises exception because quotient is too large for 32bit register.
+  __ movsxd(RBX, RAX);
+  __ cmpq(RBX, RAX);
+  __ j(NOT_EQUAL, &not_32bit);
+  __ movsxd(RBX, RCX);
+  __ cmpq(RBX, RCX);
+  __ j(NOT_EQUAL, &not_32bit);
+
+  // Both operands are 31bit smis. Divide using 32bit idiv.
   __ SmiUntag(RAX);
+  __ SmiUntag(RCX);
+  __ cdq();
+  __ idivl(RCX);
+  __ movsxd(RAX, RAX);
+  __ SmiTag(RAX);  // Result is guaranteed to fit into a smi.
+  __ ret();
+
+  // Divide using 64bit idiv.
+  __ Bind(&not_32bit);
+  __ SmiUntag(RAX);
+  __ SmiUntag(RCX);
   __ pushq(RDX);  // Preserve RDX in case of 'fall_through'.
   __ cqo();
   __ idivq(RCX);
diff --git a/runtime/vm/object.cc b/runtime/vm/object.cc
index 3c1643c..ab405fa 100644
--- a/runtime/vm/object.cc
+++ b/runtime/vm/object.cc
@@ -575,7 +575,7 @@
 
 // Make unused space in an object whose type has been transformed safe
 // for traversing during GC.
-// The unused part of the transformed object is marked as an Int8Array
+// The unused part of the transformed object is marked as an TypedDataInt8Array
 // object.
 void Object::MakeUnusedSpaceTraversable(const Object& obj,
                                         intptr_t original_size,
@@ -587,16 +587,16 @@
     intptr_t leftover_size = original_size - used_size;
 
     uword addr = RawObject::ToAddr(obj.raw()) + used_size;
-    ASSERT(Int8Array::InstanceSize(0) == Object::InstanceSize());
-    // Update the leftover space as an Int8Array object.
-    RawInt8Array* raw =
-        reinterpret_cast<RawInt8Array*>(RawObject::FromAddr(addr));
+    ASSERT(TypedData::InstanceSize(0) == Object::InstanceSize());
+    // Update the leftover space as an TypedDataInt8Array object.
+    RawTypedData* raw =
+        reinterpret_cast<RawTypedData*>(RawObject::FromAddr(addr));
     uword tags = 0;
     tags = RawObject::SizeTag::update(leftover_size, tags);
-    tags = RawObject::ClassIdTag::update(kInt8ArrayCid, tags);
+    tags = RawObject::ClassIdTag::update(kTypedDataInt8ArrayCid, tags);
     raw->ptr()->tags_ = tags;
-    intptr_t leftover_len = (leftover_size - Int8Array::InstanceSize(0));
-    ASSERT(Int8Array::InstanceSize(leftover_len) == leftover_size);
+    intptr_t leftover_len = (leftover_size - TypedData::InstanceSize(0));
+    ASSERT(TypedData::InstanceSize(leftover_len) == leftover_size);
     raw->ptr()->length_ = Smi::New(leftover_len);
   }
 }
@@ -870,8 +870,6 @@
   object_store->set_##object_store_name##_class(cls);                          \
   RegisterPrivateClass(cls, Symbols::_##name(), lib);                          \
 
-  REGISTER_SCALARLIST_CLASS(Float32x4, float32x4);
-  REGISTER_SCALARLIST_CLASS(Uint32x4, uint32x4);
   REGISTER_SCALARLIST_CLASS(Int8Array, int8_array);
   REGISTER_SCALARLIST_CLASS(Uint8Array, uint8_array);
   REGISTER_SCALARLIST_CLASS(Uint8ClampedArray, uint8_clamped_array);
@@ -881,7 +879,6 @@
   REGISTER_SCALARLIST_CLASS(Uint32Array, uint32_array);
   REGISTER_SCALARLIST_CLASS(Int64Array, int64_array);
   REGISTER_SCALARLIST_CLASS(Uint64Array, uint64_array);
-  REGISTER_SCALARLIST_CLASS(Float32x4Array, float32x4_array);
   REGISTER_SCALARLIST_CLASS(Float32Array, float32_array);
   REGISTER_SCALARLIST_CLASS(Float64Array, float64_array);
   REGISTER_SCALARLIST_CLASS(ExternalInt8Array, external_int8_array);
@@ -894,18 +891,20 @@
   REGISTER_SCALARLIST_CLASS(ExternalUint32Array, external_uint32_array);
   REGISTER_SCALARLIST_CLASS(ExternalInt64Array, external_int64_array);
   REGISTER_SCALARLIST_CLASS(ExternalUint64Array, external_uint64_array);
-  REGISTER_SCALARLIST_CLASS(ExternalFloat32x4Array, external_float32x4_array);
   REGISTER_SCALARLIST_CLASS(ExternalFloat32Array, external_float32_array);
   REGISTER_SCALARLIST_CLASS(ExternalFloat64Array, external_float64_array);
 #undef REGISTER_SCALARLIST_CLASS
 
+
   // Pre-register the typeddata library so the native class implementations
   // can be hooked up before compiling it.
   LOAD_LIBRARY(TypedData, typeddata);
   ASSERT(!lib.IsNull());
   ASSERT(lib.raw() == Library::TypedDataLibrary());
+  const intptr_t typeddata_class_array_length =
+      RawObject::NumberOfTypedDataClasses() + 2;  // +2 for Float32x4 & Uint32x4
   Array& typeddata_classes =
-      Array::Handle(Array::New(RawObject::NumberOfTypedDataClasses()));
+      Array::Handle(Array::New(typeddata_class_array_length));
   int index = 0;
 #define REGISTER_TYPED_DATA_CLASS(clazz)                                       \
   cls = Class::NewTypedDataClass(kTypedData##clazz##Cid);                      \
@@ -915,6 +914,20 @@
 
   CLASS_LIST_TYPED_DATA(REGISTER_TYPED_DATA_CLASS);
 #undef REGISTER_TYPED_DATA_CLASS
+#define REGISTER_TYPED_DATA_VIEW_CLASS(clazz)                                  \
+  cls = Class::NewTypedDataViewClass(kTypedData##clazz##ViewCid);              \
+  index = kTypedData##clazz##ViewCid - kTypedDataInt8ArrayCid;                 \
+  typeddata_classes.SetAt(index, cls);                                         \
+  RegisterPrivateClass(cls, Symbols::_##clazz##View(), lib);                   \
+  pending_classes.Add(cls, Heap::kOld);                                        \
+
+  CLASS_LIST_TYPED_DATA(REGISTER_TYPED_DATA_VIEW_CLASS);
+  cls = Class::NewTypedDataViewClass(kByteDataViewCid);
+  index = kByteDataViewCid - kTypedDataInt8ArrayCid;
+  typeddata_classes.SetAt(index, cls);
+  RegisterPrivateClass(cls, Symbols::_ByteDataView(), lib);
+  pending_classes.Add(cls, Heap::kOld);
+#undef REGISTER_TYPED_DATA_VIEW_CLASS
 #define REGISTER_EXT_TYPED_DATA_CLASS(clazz)                                   \
   cls = Class::NewExternalTypedDataClass(kExternalTypedData##clazz##Cid);      \
   index = kExternalTypedData##clazz##Cid - kTypedDataInt8ArrayCid;             \
@@ -923,6 +936,17 @@
 
   CLASS_LIST_TYPED_DATA(REGISTER_EXT_TYPED_DATA_CLASS);
 #undef REGISTER_EXT_TYPED_DATA_CLASS
+  // Add Float32x4 and Uint32x4 to dart:typeddata and register them in the
+  // object store.
+  cls = Class::New<Float32x4>();
+  object_store->set_float32x4_class(cls);
+  typeddata_classes.SetAt(typeddata_class_array_length-2, cls);
+  RegisterPrivateClass(cls, Symbols::_Float32x4(), lib);
+  cls = Class::New<Uint32x4>();
+  object_store->set_uint32x4_class(cls);
+  typeddata_classes.SetAt(typeddata_class_array_length-1, cls);
+  RegisterPrivateClass(cls, Symbols::_Uint32x4(), lib);
+
   object_store->set_typeddata_classes(typeddata_classes);
 
   // Set the super type of class Stacktrace to Object type so that the
@@ -1075,8 +1099,6 @@
   cls = Class::New<name>();                                                    \
   object_store->set_##object_store_name##_class(cls);                          \
 
-  REGISTER_SCALARLIST_CLASS(Float32x4, float32x4);
-  REGISTER_SCALARLIST_CLASS(Uint32x4, uint32x4);
   REGISTER_SCALARLIST_CLASS(Int8Array, int8_array);
   REGISTER_SCALARLIST_CLASS(Uint8Array, uint8_array);
   REGISTER_SCALARLIST_CLASS(Uint8ClampedArray, uint8_clamped_array);
@@ -1086,7 +1108,6 @@
   REGISTER_SCALARLIST_CLASS(Uint32Array, uint32_array);
   REGISTER_SCALARLIST_CLASS(Int64Array, int64_array);
   REGISTER_SCALARLIST_CLASS(Uint64Array, uint64_array);
-  REGISTER_SCALARLIST_CLASS(Float32x4Array, float32x4_array);
   REGISTER_SCALARLIST_CLASS(Float32Array, float32_array);
   REGISTER_SCALARLIST_CLASS(Float64Array, float64_array);
   REGISTER_SCALARLIST_CLASS(ExternalInt8Array, external_int8_array);
@@ -1099,7 +1120,6 @@
   REGISTER_SCALARLIST_CLASS(ExternalUint32Array, external_uint32_array);
   REGISTER_SCALARLIST_CLASS(ExternalInt64Array, external_int64_array);
   REGISTER_SCALARLIST_CLASS(ExternalUint64Array, external_uint64_array);
-  REGISTER_SCALARLIST_CLASS(ExternalFloat32x4Array, external_float32x4_array);
   REGISTER_SCALARLIST_CLASS(ExternalFloat32Array, external_float32_array);
   REGISTER_SCALARLIST_CLASS(ExternalFloat64Array, external_float64_array);
 #undef REGISTER_SCALARLIST_CLASS
@@ -1108,10 +1128,20 @@
   cls = Class::NewTypedDataClass(kTypedData##clazz##Cid);
   CLASS_LIST_TYPED_DATA(REGISTER_TYPED_DATA_CLASS);
 #undef REGISTER_TYPED_DATA_CLASS
+#define REGISTER_TYPED_DATA_VIEW_CLASS(clazz)                                  \
+  cls = Class::NewTypedDataViewClass(kTypedData##clazz##ViewCid);
+  CLASS_LIST_TYPED_DATA(REGISTER_TYPED_DATA_VIEW_CLASS);
+  cls = Class::NewTypedDataViewClass(kByteDataViewCid);
+#undef REGISTER_TYPED_DATA_VIEW_CLASS
 #define REGISTER_EXT_TYPED_DATA_CLASS(clazz)                                   \
   cls = Class::NewExternalTypedDataClass(kExternalTypedData##clazz##Cid);
   CLASS_LIST_TYPED_DATA(REGISTER_EXT_TYPED_DATA_CLASS);
 #undef REGISTER_EXT_TYPED_DATA_CLASS
+  // Add Float32x4 and Uint32x4 to the object store.
+  cls = Class::New<Float32x4>();
+  object_store->set_float32x4_class(cls);
+  cls = Class::New<Uint32x4>();
+  object_store->set_uint32x4_class(cls);
 
   cls = Class::New<Integer>();
   object_store->set_integer_implementation_class(cls);
@@ -1340,9 +1370,6 @@
     case kUint64ArrayCid:
     case kExternalUint64ArrayCid:
       return Symbols::Uint64List().raw();
-    case kFloat32x4ArrayCid:
-    case kExternalFloat32x4ArrayCid:
-      return Symbols::Float32x4List().raw();
     case kFloat32ArrayCid:
     case kExternalFloat32ArrayCid:
       return Symbols::Float32List().raw();
@@ -1952,6 +1979,15 @@
 }
 
 
+RawClass* Class::NewTypedDataViewClass(intptr_t class_id) {
+  ASSERT(RawObject::IsTypedDataViewClassId(class_id));
+  Class& result = Class::Handle(New<Instance>(class_id));
+  result.set_instance_size(0);
+  result.set_next_field_offset(0);
+  return result.raw();
+}
+
+
 RawClass* Class::NewExternalTypedDataClass(intptr_t class_id) {
   ASSERT(RawObject::IsExternalTypedDataClassId(class_id));
   intptr_t instance_size = ExternalTypedData::InstanceSize();
@@ -3873,8 +3909,11 @@
   const intptr_t num_ignored_params =
       (other.IsRedirectingFactory() && IsConstructor()) ? 1 : 0;
   // The default values of optional parameters can differ.
-  if (((num_fixed_params - num_ignored_params) != other_num_fixed_params) ||
-      (num_opt_pos_params < other_num_opt_pos_params) ||
+  // This function requires the same arguments or less and accepts the same
+  // arguments or more.
+  if (((num_fixed_params - num_ignored_params) > other_num_fixed_params) ||
+      ((num_fixed_params - num_ignored_params) + num_opt_pos_params <
+       other_num_fixed_params + other_num_opt_pos_params) ||
       (num_opt_named_params < other_num_opt_named_params)) {
     return false;
   }
@@ -3971,8 +4010,11 @@
       other.NumOptionalPositionalParameters();
   const intptr_t other_num_opt_named_params =
       other.NumOptionalNamedParameters();
-  if ((num_fixed_params != other_num_fixed_params) ||
-      (num_opt_pos_params < other_num_opt_pos_params) ||
+  // This function requires the same arguments or less and accepts the same
+  // arguments or more.
+  if ((num_fixed_params > other_num_fixed_params) ||
+      (num_fixed_params + num_opt_pos_params <
+       other_num_fixed_params + other_num_opt_pos_params) ||
       (num_opt_named_params < other_num_opt_named_params)) {
     return false;
   }
@@ -4005,7 +4047,8 @@
     }
   }
   // Check the types of fixed and optional positional parameters.
-  for (intptr_t i = 0; i < num_fixed_params + other_num_opt_pos_params; i++) {
+  for (intptr_t i = 0;
+       i < other_num_fixed_params + other_num_opt_pos_params; i++) {
     if (!TestParameterType(test_kind,
                            i, i, type_arguments, other, other_type_arguments,
                            malformed_error)) {
@@ -4943,12 +4986,12 @@
 }
 
 
-RawExternalUint8Array* TokenStream::GetStream() const {
+RawExternalTypedData* TokenStream::GetStream() const {
   return raw_ptr()->stream_;
 }
 
 
-void TokenStream::SetStream(const ExternalUint8Array& value) const {
+void TokenStream::SetStream(const ExternalTypedData& value) const {
   StorePointer(&raw_ptr()->stream_, value.raw());
 }
 
@@ -4972,7 +5015,7 @@
 
 RawString* TokenStream::GenerateSource() const {
   Iterator iterator(*this, 0);
-  const ExternalUint8Array& data = ExternalUint8Array::Handle(GetStream());
+  const ExternalTypedData& data = ExternalTypedData::Handle(GetStream());
   const GrowableObjectArray& literals =
       GrowableObjectArray::Handle(GrowableObjectArray::New(data.Length()));
   const String& private_key = String::Handle(PrivateKey());
@@ -5154,8 +5197,9 @@
   }
   uint8_t* data = reinterpret_cast<uint8_t*>(::malloc(len));
   ASSERT(data != NULL);
-  const ExternalUint8Array& stream = ExternalUint8Array::Handle(
-      ExternalUint8Array::New(data, len, Heap::kOld));
+  const ExternalTypedData& stream = ExternalTypedData::Handle(
+      ExternalTypedData::New(kExternalTypedDataUint8ArrayCid,
+                             data, len, Heap::kOld));
   stream.AddFinalizer(data, DataFinalizer);
   const TokenStream& result = TokenStream::Handle(TokenStream::New());
   result.SetStream(stream);
@@ -5166,10 +5210,10 @@
 // Helper class for creation of compressed token stream data.
 class CompressedTokenStreamData : public ValueObject {
  public:
-  static const intptr_t kIncrementSize = 16 * KB;
+  static const intptr_t kInitialSize = 16 * KB;
   CompressedTokenStreamData() :
       buffer_(NULL),
-      stream_(&buffer_, Reallocate, kIncrementSize),
+      stream_(&buffer_, Reallocate, kInitialSize),
       token_objects_(GrowableObjectArray::Handle(
           GrowableObjectArray::New(kInitialTokenCount, Heap::kOld))),
       token_obj_(Object::Handle()),
@@ -5328,8 +5372,9 @@
   data.AddSimpleToken(Token::kEOS);  // End of stream.
 
   // Create and setup the token stream object.
-  const ExternalUint8Array& stream = ExternalUint8Array::Handle(
-      ExternalUint8Array::New(data.GetStream(), data.Length(), Heap::kOld));
+  const ExternalTypedData& stream = ExternalTypedData::Handle(
+      ExternalTypedData::New(kExternalTypedDataUint8ArrayCid,
+                             data.GetStream(), data.Length(), Heap::kOld));
   stream.AddFinalizer(data.GetStream(), DataFinalizer);
   const TokenStream& result = TokenStream::Handle(New());
   result.SetPrivateKey(private_key);
@@ -5350,8 +5395,8 @@
 
 TokenStream::Iterator::Iterator(const TokenStream& tokens, intptr_t token_pos)
     : tokens_(TokenStream::Handle(tokens.raw())),
-      data_(ExternalUint8Array::Handle(tokens.GetStream())),
-      stream_(data_.ByteAddr(0), data_.Length()),
+      data_(ExternalTypedData::Handle(tokens.GetStream())),
+      stream_(reinterpret_cast<uint8_t*>(data_.DataAddr(0)), data_.Length()),
       token_objects_(Array::Handle(tokens.TokenObjects())),
       obj_(Object::Handle()),
       cur_token_pos_(token_pos),
@@ -5365,7 +5410,8 @@
                                       intptr_t token_pos) {
   tokens_ = tokens.raw();
   data_ = tokens.GetStream();
-  stream_.SetStream(data_.ByteAddr(0), data_.Length());
+  stream_.SetStream(reinterpret_cast<uint8_t*>(data_.DataAddr(0)),
+                    data_.Length());
   token_objects_ = tokens.TokenObjects();
   obj_ = Object::null();
   cur_token_pos_ = token_pos;
@@ -7674,13 +7720,6 @@
 
   // Allocate the code object.
   Code& code = Code::ZoneHandle(Code::New(pointer_offsets.length()));
-
-  // Clone the object pool in the old space, if necessary.
-  Array& object_pool = Array::Handle(
-      Array::MakeArray(assembler->object_pool()));
-  if (!object_pool.IsOld()) {
-    object_pool ^= Object::Clone(object_pool, Heap::kOld);
-  }
   {
     NoGCScope no_gc;
 
@@ -7699,7 +7738,15 @@
     code.set_instructions(instrs.raw());
 
     // Set object pool in Instructions object.
-    instrs.set_object_pool(object_pool.raw());
+    const GrowableObjectArray& object_pool = assembler->object_pool();
+    if (object_pool.IsNull()) {
+      instrs.set_object_pool(Object::empty_array().raw());
+    } else {
+      // TODO(regis): Once MakeArray takes a Heap::Space argument, call it here
+      // with Heap::kOld and change the ARM and MIPS assemblers to work with a
+      // GrowableObjectArray in new space.
+      instrs.set_object_pool(Array::MakeArray(object_pool));
+    }
   }
   return code.raw();
 }
@@ -12209,10 +12256,11 @@
 
 
 RawArray* Array::MakeArray(const GrowableObjectArray& growable_array) {
-  if (growable_array.IsNull()) {
-    return Array::null();
-  }
+  ASSERT(!growable_array.IsNull());
   intptr_t used_len = growable_array.Length();
+  if (used_len == 0) {
+    return Object::empty_array().raw();
+  }
   intptr_t capacity_len = growable_array.Capacity();
   Isolate* isolate = Isolate::Current();
   const Array& array = Array::Handle(isolate, growable_array.data());
@@ -12565,17 +12613,18 @@
 
 
 const intptr_t TypedData::element_size[] = {
-  1,  // kTypedDataInt8ArrayCid.
-  1,  // kTypedDataUint8ArrayCid.
-  1,  // kTypedDataUint8ClampedArrayCid.
-  2,  // kTypedDataInt16ArrayCid.
-  2,  // kTypedDataUint16ArrayCid.
-  4,  // kTypedDataInt32ArrayCid.
-  4,  // kTypedDataUint32ArrayCid.
-  8,  // kTypedDataInt64ArrayCid.
-  8,  // kTypedDataUint64ArrayCid.
-  4,  // kTypedDataFloat32ArrayCid.
-  8,  // kTypedDataFloat64ArrayCid.
+  1,   // kTypedDataInt8ArrayCid.
+  1,   // kTypedDataUint8ArrayCid.
+  1,   // kTypedDataUint8ClampedArrayCid.
+  2,   // kTypedDataInt16ArrayCid.
+  2,   // kTypedDataUint16ArrayCid.
+  4,   // kTypedDataInt32ArrayCid.
+  4,   // kTypedDataUint32ArrayCid.
+  8,   // kTypedDataInt64ArrayCid.
+  8,   // kTypedDataUint64ArrayCid.
+  4,   // kTypedDataFloat32ArrayCid.
+  8,   // kTypedDataFloat64ArrayCid.
+  16,  // kTypedDataFloat32x4ArrayCid.
 };
 
 
@@ -13015,30 +13064,6 @@
 }
 
 
-RawFloat32x4Array* Float32x4Array::New(intptr_t len,
-                                       Heap::Space space) {
-  ASSERT(Isolate::Current()->object_store()->float32x4_array_class() !=
-         Class::null());
-  return NewImpl<Float32x4Array, RawFloat32x4Array>(kClassId, len,
-                                                              space);
-}
-
-
-RawFloat32x4Array* Float32x4Array::New(const simd128_value_t* data,
-                                       intptr_t len,
-                                       Heap::Space space) {
-  ASSERT(Isolate::Current()->object_store()->float32_array_class() !=
-         Class::null());
-  return NewImpl<Float32x4Array, RawFloat32x4Array>(kClassId, data,
-                                                              len, space);
-}
-
-
-const char* Float32x4Array::ToCString() const {
-  return "_Float32x4Array";
-}
-
-
 RawFloat32Array* Float32Array::New(intptr_t len, Heap::Space space) {
   ASSERT(Isolate::Current()->object_store()->float32_array_class() !=
          Class::null());
@@ -13219,23 +13244,6 @@
 }
 
 
-RawExternalFloat32x4Array* ExternalFloat32x4Array::New(simd128_value_t* data,
-                                                       intptr_t len,
-                                                       Heap::Space space) {
-  RawClass* cls =
-     Isolate::Current()->object_store()->external_float32x4_array_class();
-  ASSERT(cls != Class::null());
-  return NewExternalImpl<ExternalFloat32x4Array,
-                         RawExternalFloat32x4Array>(kClassId, data, len,
-                                                    space);
-}
-
-
-const char* ExternalFloat32x4Array::ToCString() const {
-  return "_ExternalFloat32x4Array";
-}
-
-
 RawExternalFloat32Array* ExternalFloat32Array::New(float* data,
                                                    intptr_t len,
                                                    Heap::Space space) {
diff --git a/runtime/vm/object.h b/runtime/vm/object.h
index 21b5fec..bac2f69 100644
--- a/runtime/vm/object.h
+++ b/runtime/vm/object.h
@@ -836,6 +836,9 @@
   // Allocate the raw TypedData classes.
   static RawClass* NewTypedDataClass(intptr_t class_id);
 
+  // Allocate the raw TypedDataView classes.
+  static RawClass* NewTypedDataViewClass(intptr_t class_id);
+
   // Allocate the raw ExternalTypedData classes.
   static RawClass* NewExternalTypedDataClass(intptr_t class_id);
 
@@ -1895,8 +1898,8 @@
   RawArray* TokenObjects() const;
   void SetTokenObjects(const Array& value) const;
 
-  RawExternalUint8Array* GetStream() const;
-  void SetStream(const ExternalUint8Array& stream) const;
+  RawExternalTypedData* GetStream() const;
+  void SetStream(const ExternalTypedData& stream) const;
 
   RawString* GenerateSource() const;
   intptr_t ComputeSourcePosition(intptr_t tok_pos) const;
@@ -1949,7 +1952,7 @@
     }
 
     TokenStream& tokens_;
-    ExternalUint8Array& data_;
+    ExternalTypedData& data_;
     ReadStream stream_;
     Array& token_objects_;
     Object& obj_;
@@ -2325,8 +2328,7 @@
     raw_ptr()->code_ = code;
   }
   void set_object_pool(RawArray* object_pool) const {
-    ASSERT(object_pool->IsOldObject());
-    raw_ptr()->object_pool_ = object_pool;
+    StorePointer(&raw_ptr()->object_pool_, object_pool);
   }
 
   // New is a private method as RawInstruction and RawCode objects should
@@ -5049,6 +5051,7 @@
   TYPED_GETTER_SETTER(Uint64, uint64_t)
   TYPED_GETTER_SETTER(Float32, float)
   TYPED_GETTER_SETTER(Float64, double)
+  TYPED_GETTER_SETTER(Float32x4, simd128_value_t)
 
   static intptr_t length_offset() {
     return OFFSET_OF(RawTypedData, length_);
@@ -5145,6 +5148,7 @@
   TYPED_GETTER_SETTER(Uint64, uint64_t)
   TYPED_GETTER_SETTER(Float32, float)
   TYPED_GETTER_SETTER(Float64, double)
+  TYPED_GETTER_SETTER(Float32x4, simd128_value_t);
 
   FinalizablePersistentHandle* AddFinalizer(
       void* peer, Dart_WeakPersistentHandleFinalizer callback) const;
@@ -5741,59 +5745,6 @@
 };
 
 
-class Float32x4Array : public ByteArray {
- public:
-  intptr_t ByteLength() const {
-    return Length() * kBytesPerElement;
-  }
-
-  simd128_value_t At(intptr_t index) const {
-    ASSERT((index >= 0) && (index < Length()));
-    return raw_ptr()->data_[index];
-  }
-
-  void SetAt(intptr_t index, simd128_value_t value) const {
-    ASSERT((index >= 0) && (index < Length()));
-    raw_ptr()->data_[index] = value;
-  }
-
-  static const intptr_t kBytesPerElement = 16;
-  static const intptr_t kMaxElements = kSmiMax / kBytesPerElement;
-
-  static intptr_t data_offset() {
-    return OFFSET_OF(RawFloat32x4Array, data_);
-  }
-
-  static intptr_t InstanceSize() {
-    ASSERT(sizeof(RawFloat32x4Array) ==
-           OFFSET_OF(RawFloat32x4Array, data_));
-    return 0;
-  }
-
-  static intptr_t InstanceSize(intptr_t len) {
-    ASSERT(0 <= len && len <= kMaxElements);
-    return RoundedAllocationSize(
-        sizeof(RawFloat32x4Array) + (len * kBytesPerElement));
-  }
-
-  static RawFloat32x4Array* New(intptr_t len,
-                                     Heap::Space space = Heap::kNew);
-  static RawFloat32x4Array* New(const simd128_value_t* data,
-                                     intptr_t len,
-                                     Heap::Space space = Heap::kNew);
-
- private:
-  uint8_t* ByteAddr(intptr_t byte_offset) const {
-    ASSERT((byte_offset >= 0) && (byte_offset < ByteLength()));
-    return reinterpret_cast<uint8_t*>(&raw_ptr()->data_) + byte_offset;
-  }
-
-  FINAL_HEAP_OBJECT_IMPLEMENTATION(Float32x4Array, ByteArray);
-  friend class ByteArray;
-  friend class Class;
-};
-
-
 class Float32Array : public ByteArray {
  public:
   intptr_t ByteLength() const {
@@ -6393,65 +6344,6 @@
 };
 
 
-class ExternalFloat32x4Array : public ByteArray {
- public:
-  intptr_t ByteLength() const {
-    return Length() * kBytesPerElement;
-  }
-
-  simd128_value_t At(intptr_t index) const {
-    ASSERT((index >= 0) && (index < Length()));
-    return raw_ptr()->data_[index];
-  }
-
-  void SetAt(intptr_t index, simd128_value_t value) const {
-    ASSERT((index >= 0) && (index < Length()));
-    raw_ptr()->data_[index] = value;
-  }
-
-
-  simd128_value_t* GetData() const {
-    return raw_ptr()->data_;
-  }
-
-  void* GetPeer() const {
-    return raw_ptr()->peer_;
-  }
-
-  static const intptr_t kBytesPerElement = 16;
-
-  // Since external arrays may be serialized to non-external ones,
-  // enforce the same maximum element count.
-  static const intptr_t kMaxElements = Float32x4Array::kMaxElements;
-
-  static intptr_t InstanceSize() {
-    return RoundedAllocationSize(sizeof(RawExternalFloat32x4Array));
-  }
-
-  static RawExternalFloat32x4Array* New(simd128_value_t* data, intptr_t len,
-                                        Heap::Space space = Heap::kNew);
-
- private:
-  uint8_t* ByteAddr(intptr_t byte_offset) const {
-    ASSERT((byte_offset >= 0) && (byte_offset < ByteLength()));
-    uint8_t* data = reinterpret_cast<uint8_t*>(raw_ptr()->data_);
-    return data + byte_offset;
-  }
-
-  void SetData(simd128_value_t* data) const {
-    raw_ptr()->data_ = data;
-  }
-
-  void SetPeer(void* peer) const {
-    raw_ptr()->peer_ = peer;
-  }
-
-  FINAL_HEAP_OBJECT_IMPLEMENTATION(ExternalFloat32x4Array, ByteArray);
-  friend class ByteArray;
-  friend class Class;
-};
-
-
 class ExternalFloat32Array : public ByteArray {
  public:
   intptr_t ByteLength() const {
diff --git a/runtime/vm/object_store.cc b/runtime/vm/object_store.cc
index a59973d..bc63877 100644
--- a/runtime/vm/object_store.cc
+++ b/runtime/vm/object_store.cc
@@ -39,6 +39,8 @@
     array_type_(Type::null()),
     immutable_array_class_(Class::null()),
     growable_object_array_class_(Class::null()),
+    float32x4_class_(Class::null()),
+    uint32x4_class_(Class::null()),
     int8_array_class_(Class::null()),
     uint8_array_class_(Class::null()),
     uint8_clamped_array_class_(Class::null()),
diff --git a/runtime/vm/object_store.h b/runtime/vm/object_store.h
index 60131b5..573beac 100644
--- a/runtime/vm/object_store.h
+++ b/runtime/vm/object_store.h
@@ -251,13 +251,6 @@
     uint64_array_class_ = value.raw();
   }
 
-  RawClass* float32x4_array_class() const {
-    return float32x4_array_class_;
-  }
-  void set_float32x4_array_class(const Class& value) {
-    float32x4_array_class_ = value.raw();
-  }
-
   RawClass* float32_array_class() const {
     return float32_array_class_;
   }
@@ -335,12 +328,6 @@
     external_uint64_array_class_ = value.raw();
   }
 
-  RawClass* external_float32x4_array_class() const {
-    return external_float32x4_array_class_;
-  }
-  void set_external_float32x4_array_class(const Class& value) {
-    external_float32x4_array_class_ = value.raw();
-  }
 
   RawClass* external_float32_array_class() const {
     return external_float32_array_class_;
@@ -640,7 +627,6 @@
   RawClass* uint32_array_class_;
   RawClass* int64_array_class_;
   RawClass* uint64_array_class_;
-  RawClass* float32x4_array_class_;
   RawClass* float32_array_class_;
   RawClass* float64_array_class_;
   RawClass* external_int8_array_class_;
@@ -652,7 +638,6 @@
   RawClass* external_uint32_array_class_;
   RawClass* external_int64_array_class_;
   RawClass* external_uint64_array_class_;
-  RawClass* external_float32x4_array_class_;
   RawClass* external_float32_array_class_;
   RawClass* external_float64_array_class_;
   RawArray* typeddata_classes_;
diff --git a/runtime/vm/object_test.cc b/runtime/vm/object_test.cc
index e78f306..44d6e61 100644
--- a/runtime/vm/object_test.cc
+++ b/runtime/vm/object_test.cc
@@ -1761,7 +1761,7 @@
   // object is properly setup.
   // 1. Should produce an array of length 2 and a left over int8 array.
   Array& new_array = Array::Handle();
-  Int8Array& left_over_array = Int8Array::Handle();
+  TypedData& left_over_array = TypedData::Handle();
   Object& obj = Object::Handle();
   uword addr = 0;
   intptr_t used_size = 0;
@@ -1782,7 +1782,7 @@
   EXPECT_EQ(2, new_array.Length());
   addr += used_size;
   obj = RawObject::FromAddr(addr);
-  EXPECT(obj.IsInt8Array());
+  EXPECT(obj.IsTypedData());
   left_over_array ^= obj.raw();
   EXPECT_EQ((2 * kWordSize), left_over_array.Length());
 
@@ -1803,7 +1803,7 @@
   EXPECT_EQ(3, new_array.Length());
   addr += used_size;
   obj = RawObject::FromAddr(addr);
-  EXPECT(obj.IsInt8Array());
+  EXPECT(obj.IsTypedData());
   left_over_array ^= obj.raw();
   EXPECT_EQ(0, left_over_array.Length());
 
@@ -1824,545 +1824,137 @@
   EXPECT_EQ(1, new_array.Length());
   addr += used_size;
   obj = RawObject::FromAddr(addr);
-  EXPECT(obj.IsInt8Array());
+  EXPECT(obj.IsTypedData());
   left_over_array ^= obj.raw();
   EXPECT_EQ((6 * kWordSize), left_over_array.Length());
 }
 
 
-TEST_CASE(InternalByteArray) {
+TEST_CASE(InternalTypedData) {
   uint8_t data[] = { 253, 254, 255, 0, 1, 2, 3, 4 };
   intptr_t data_length = ARRAY_SIZE(data);
 
-  const Int8Array& int8_array =
-      Int8Array::Handle(Int8Array::New(reinterpret_cast<int8_t*>(data),
-                                       data_length));
+  const TypedData& int8_array =
+      TypedData::Handle(TypedData::New(kTypedDataInt8ArrayCid, data_length));
   EXPECT(!int8_array.IsNull());
   EXPECT_EQ(data_length, int8_array.Length());
+  for (intptr_t i = 0; i < data_length; ++i) {
+    int8_array.SetInt8(i, data[i]);
+  }
 
-  EXPECT_EQ(-3, int8_array.At(0));
-  uint8_t at_0;
-  ByteArray::Copy(&at_0, int8_array, 0, sizeof(at_0));
-  EXPECT_EQ(253, at_0);
+  EXPECT_EQ(-3, int8_array.GetInt8(0));
+  EXPECT_EQ(253, int8_array.GetUint8(0));
 
-  EXPECT_EQ(-2, int8_array.At(1));
-  uint8_t at_1;
-  ByteArray::Copy(&at_1, int8_array, 1, sizeof(at_1));
-  EXPECT_EQ(254, at_1);
+  EXPECT_EQ(-2, int8_array.GetInt8(1));
+  EXPECT_EQ(254, int8_array.GetUint8(1));
 
-  EXPECT_EQ(-1, int8_array.At(2));
-  uint8_t at_2;
-  ByteArray::Copy(&at_2, int8_array, 2, sizeof(at_2));
-  EXPECT_EQ(255, at_2);
+  EXPECT_EQ(-1, int8_array.GetInt8(2));
+  EXPECT_EQ(255, int8_array.GetUint8(2));
 
-  EXPECT_EQ(0, int8_array.At(3));
-  uint8_t at_3;
-  ByteArray::Copy(&at_3, int8_array, 3, sizeof(at_3));
-  EXPECT_EQ(0, at_3);
+  EXPECT_EQ(0, int8_array.GetInt8(3));
+  EXPECT_EQ(0, int8_array.GetUint8(3));
 
-  EXPECT_EQ(1, int8_array.At(4));
-  uint8_t at_4;
-  ByteArray::Copy(&at_4, int8_array, 4, sizeof(at_4));
-  EXPECT_EQ(1, at_4);
+  EXPECT_EQ(1, int8_array.GetInt8(4));
+  EXPECT_EQ(1, int8_array.GetUint8(4));
 
-  EXPECT_EQ(2, int8_array.At(5));
-  uint8_t at_5;
-  ByteArray::Copy(&at_5, int8_array, 5, sizeof(at_5));
-  EXPECT_EQ(2, at_5);
+  EXPECT_EQ(2, int8_array.GetInt8(5));
+  EXPECT_EQ(2, int8_array.GetUint8(5));
 
-  EXPECT_EQ(3, int8_array.At(6));
-  uint8_t at_6;
-  ByteArray::Copy(&at_6, int8_array, 6, sizeof(at_6));
-  EXPECT_EQ(3, at_6);
+  EXPECT_EQ(3, int8_array.GetInt8(6));
+  EXPECT_EQ(3, int8_array.GetUint8(6));
 
-  EXPECT_EQ(4, int8_array.At(7));
-  uint8_t at_7;
-  ByteArray::Copy(&at_7, int8_array, 7, sizeof(at_7));
-  EXPECT_EQ(4, at_7);
+  EXPECT_EQ(4, int8_array.GetInt8(7));
+  EXPECT_EQ(4, int8_array.GetUint8(7));
 
-  const Int8Array& int8_array2 =
-      Int8Array::Handle(Int8Array::New(reinterpret_cast<int8_t*>(data),
-                                       data_length));
+  const TypedData& int8_array2 =
+      TypedData::Handle(TypedData::New(kTypedDataInt8ArrayCid, data_length));
   EXPECT(!int8_array.IsNull());
   EXPECT_EQ(data_length, int8_array.Length());
+  for (intptr_t i = 0; i < data_length; ++i) {
+    int8_array2.SetInt8(i, data[i]);
+  }
 
   for (intptr_t i = 0; i < data_length; ++i) {
-    EXPECT_EQ(int8_array.At(i), int8_array2.At(i));
+    EXPECT_EQ(int8_array.GetInt8(i), int8_array2.GetInt8(i));
   }
   for (intptr_t i = 0; i < data_length; ++i) {
-    int8_array.SetAt(i, 123 + i);
+    int8_array.SetInt8(i, 123 + i);
   }
   for (intptr_t i = 0; i < data_length; ++i) {
-    EXPECT(int8_array.At(i) != int8_array2.At(i));
+    EXPECT(int8_array.GetInt8(i) != int8_array2.GetInt8(i));
   }
 }
 
 
-TEST_CASE(ExternalByteArray) {
+TEST_CASE(ExternalTypedData) {
   uint8_t data[] = { 253, 254, 255, 0, 1, 2, 3, 4 };
   intptr_t data_length = ARRAY_SIZE(data);
 
-  const ExternalInt8Array& int8_array =
-      ExternalInt8Array::Handle(
-          ExternalInt8Array::New(reinterpret_cast<int8_t*>(data),
+  const ExternalTypedData& int8_array =
+      ExternalTypedData::Handle(
+          ExternalTypedData::New(kExternalTypedDataInt8ArrayCid,
+                                 data,
                                  data_length));
   EXPECT(!int8_array.IsNull());
   EXPECT_EQ(data_length, int8_array.Length());
 
-  const ExternalUint8Array& uint8_array =
-      ExternalUint8Array::Handle(
-          ExternalUint8Array::New(data, data_length));
+  const ExternalTypedData& uint8_array =
+      ExternalTypedData::Handle(
+          ExternalTypedData::New(kExternalTypedDataUint8ArrayCid,
+                                  data,
+                                  data_length));
   EXPECT(!uint8_array.IsNull());
   EXPECT_EQ(data_length, uint8_array.Length());
 
-  const ExternalUint8ClampedArray& uint8_clamped_array =
-      ExternalUint8ClampedArray::Handle(
-          ExternalUint8ClampedArray::New(data, data_length));
+  const ExternalTypedData& uint8_clamped_array =
+      ExternalTypedData::Handle(
+          ExternalTypedData::New(kExternalTypedDataUint8ClampedArrayCid,
+                                 data,
+                                 data_length));
   EXPECT(!uint8_clamped_array.IsNull());
   EXPECT_EQ(data_length, uint8_clamped_array.Length());
 
-  EXPECT_EQ(-3, int8_array.At(0));
-  EXPECT_EQ(253, uint8_array.At(0));
-  EXPECT_EQ(253, uint8_clamped_array.At(0));
+  EXPECT_EQ(-3, int8_array.GetInt8(0));
+  EXPECT_EQ(253, uint8_array.GetUint8(0));
+  EXPECT_EQ(253, uint8_clamped_array.GetUint8(0));
 
-  EXPECT_EQ(-2, int8_array.At(1));
-  EXPECT_EQ(254, uint8_array.At(1));
-  EXPECT_EQ(254, uint8_clamped_array.At(1));
+  EXPECT_EQ(-2, int8_array.GetInt8(1));
+  EXPECT_EQ(254, uint8_array.GetUint8(1));
+  EXPECT_EQ(254, uint8_clamped_array.GetUint8(1));
 
-  EXPECT_EQ(-1, int8_array.At(2));
-  EXPECT_EQ(255, uint8_array.At(2));
-  EXPECT_EQ(255, uint8_clamped_array.At(2));
+  EXPECT_EQ(-1, int8_array.GetInt8(2));
+  EXPECT_EQ(255, uint8_array.GetUint8(2));
+  EXPECT_EQ(255, uint8_clamped_array.GetUint8(2));
 
-  EXPECT_EQ(0, int8_array.At(3));
-  EXPECT_EQ(0, uint8_array.At(3));
-  EXPECT_EQ(0, uint8_clamped_array.At(3));
+  EXPECT_EQ(0, int8_array.GetInt8(3));
+  EXPECT_EQ(0, uint8_array.GetUint8(3));
+  EXPECT_EQ(0, uint8_clamped_array.GetUint8(3));
 
-  EXPECT_EQ(1, int8_array.At(4));
-  EXPECT_EQ(1, uint8_array.At(4));
-  EXPECT_EQ(1, uint8_clamped_array.At(4));
+  EXPECT_EQ(1, int8_array.GetInt8(4));
+  EXPECT_EQ(1, uint8_array.GetUint8(4));
+  EXPECT_EQ(1, uint8_clamped_array.GetUint8(4));
 
-  EXPECT_EQ(2, int8_array.At(5));
-  EXPECT_EQ(2, uint8_array.At(5));
-  EXPECT_EQ(2, uint8_clamped_array.At(5));
+  EXPECT_EQ(2, int8_array.GetInt8(5));
+  EXPECT_EQ(2, uint8_array.GetUint8(5));
+  EXPECT_EQ(2, uint8_clamped_array.GetUint8(5));
 
   for (intptr_t i = 0 ; i < int8_array.Length(); ++i) {
-    uint8_t value = 0;
-    ByteArray::Copy(&value, int8_array, i, sizeof(value));
-    EXPECT_EQ(value, uint8_array.At(i));
+    EXPECT_EQ(int8_array.GetUint8(i), uint8_array.GetUint8(i));
   }
 
-  int8_array.SetAt(2, -123);
-  uint8_array.SetAt(0, 123);
+  int8_array.SetInt8(2, -123);
+  uint8_array.SetUint8(0, 123);
   for (intptr_t i = 0 ; i < int8_array.Length(); ++i) {
-    int8_t value = 0;
-    ByteArray::Copy(&value, uint8_array, i, sizeof(value));
-    EXPECT_EQ(int8_array.At(i), value);
+    EXPECT_EQ(int8_array.GetInt8(i), uint8_array.GetInt8(i));
   }
 
-  uint8_clamped_array.SetAt(0, 123);
+  uint8_clamped_array.SetUint8(0, 123);
   for (intptr_t i = 0 ; i < int8_array.Length(); ++i) {
-    int8_t value = 0;
-    ByteArray::Copy(&value, uint8_clamped_array, i, sizeof(value));
-    EXPECT_EQ(int8_array.At(i), value);
+    EXPECT_EQ(int8_array.GetUint8(i), uint8_clamped_array.GetUint8(i));
   }
 }
 
 
-TEST_CASE(UInt8ByteArrayCopyInternal) {
-  const uint8_t b_0_1_2_3[] = { 0, 1, 2, 3 };
-  const uint8_t b_4_5_6_7[] = { 4, 5, 6, 7 };
-
-  const Uint8Array& internal =
-      Uint8Array::Handle(Uint8Array::New(b_0_1_2_3, ARRAY_SIZE(b_0_1_2_3)));
-  EXPECT(!internal.IsNull());
-  EXPECT_EQ(4, internal.Length());
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A zero length copy.
-  ByteArray::Copy(internal, 0, b_4_5_6_7, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // Another zero length copy.
-  ByteArray::Copy(internal, 4, b_4_5_6_7, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A one element copy.
-  ByteArray::Copy(internal, 0, b_4_5_6_7, 1);
-  EXPECT_EQ(4, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A two element copy.
-  ByteArray::Copy(internal, 2, b_4_5_6_7, 2);
-  EXPECT_EQ(4, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(4, internal.At(2));
-  EXPECT_EQ(5, internal.At(3));
-
-  // A three element copy.
-  ByteArray::Copy(internal, 1, b_4_5_6_7, 3);
-  EXPECT_EQ(4, internal.At(0));
-  EXPECT_EQ(4, internal.At(1));
-  EXPECT_EQ(5, internal.At(2));
-  EXPECT_EQ(6, internal.At(3));
-
-  // A four element copy.
-  ByteArray::Copy(internal, 0, b_0_1_2_3, 4);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-}
-
-TEST_CASE(ClampedUInt8ByteArrayCopyInternal) {
-  const uint8_t b_0_1_2_3[] = { 0, 1, 2, 3 };
-  const uint8_t b_4_5_6_7[] = { 4, 5, 6, 7 };
-
-  const Uint8ClampedArray& internal =
-      Uint8ClampedArray::Handle(
-          Uint8ClampedArray::New(b_0_1_2_3, ARRAY_SIZE(b_0_1_2_3)));
-  EXPECT(!internal.IsNull());
-  EXPECT_EQ(4, internal.Length());
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A zero length copy.
-  ByteArray::Copy(internal, 0, b_4_5_6_7, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // Another zero length copy.
-  ByteArray::Copy(internal, 4, b_4_5_6_7, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A one element copy.
-  ByteArray::Copy(internal, 0, b_4_5_6_7, 1);
-  EXPECT_EQ(4, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A two element copy.
-  ByteArray::Copy(internal, 2, b_4_5_6_7, 2);
-  EXPECT_EQ(4, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(4, internal.At(2));
-  EXPECT_EQ(5, internal.At(3));
-
-  // A three element copy.
-  ByteArray::Copy(internal, 1, b_4_5_6_7, 3);
-  EXPECT_EQ(4, internal.At(0));
-  EXPECT_EQ(4, internal.At(1));
-  EXPECT_EQ(5, internal.At(2));
-  EXPECT_EQ(6, internal.At(3));
-
-  // A four element copy.
-  ByteArray::Copy(internal, 0, b_0_1_2_3, 4);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-}
-
-
-TEST_CASE(Uint8ByteArrayCopyExternal) {
-  const uint8_t b_0_1_2_3[] = { 0, 1, 2, 3 };
-  const uint8_t b_4_5_6_7[] = { 4, 5, 6, 7 };
-
-  uint8_t data[] = { 0, 1, 2, 3 };
-
-  const ExternalUint8Array& external =
-      ExternalUint8Array::Handle(
-          ExternalUint8Array::New(data, ARRAY_SIZE(data)));
-  EXPECT(!external.IsNull());
-  EXPECT_EQ(4, external.Length());
-  EXPECT_EQ(0, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-
-  // A zero length copy.
-  ByteArray::Copy(external, 0, b_4_5_6_7, 0);
-  EXPECT_EQ(0, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-
-  // Another zero length copy.
-  ByteArray::Copy(external, 4, b_4_5_6_7, 0);
-  EXPECT_EQ(0, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-
-  // A one element copy.
-  ByteArray::Copy(external, 0, b_4_5_6_7, 1);
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-
-  // A two element copy.
-  ByteArray::Copy(external, 2, b_4_5_6_7, 2);
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(4, external.At(2));
-  EXPECT_EQ(5, external.At(3));
-
-  // A three element copy.
-  ByteArray::Copy(external, 1, b_4_5_6_7, 3);
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(4, external.At(1));
-  EXPECT_EQ(5, external.At(2));
-  EXPECT_EQ(6, external.At(3));
-
-  // A four element copy.
-  ByteArray::Copy(external, 0, b_0_1_2_3, 4);
-  EXPECT_EQ(0, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-}
-
-
-TEST_CASE(ClampedUint8ByteArrayCopyExternal) {
-  const uint8_t b_0_1_2_3[] = { 0, 1, 2, 3 };
-  const uint8_t b_4_5_6_7[] = { 4, 5, 6, 7 };
-
-  uint8_t data[] = { 0, 1, 2, 3 };
-
-  const ExternalUint8ClampedArray& external =
-      ExternalUint8ClampedArray::Handle(
-          ExternalUint8ClampedArray::New(data, ARRAY_SIZE(data)));
-  EXPECT(!external.IsNull());
-  EXPECT_EQ(4, external.Length());
-  EXPECT_EQ(0, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-
-  // A zero length copy.
-  ByteArray::Copy(external, 0, b_4_5_6_7, 0);
-  EXPECT_EQ(0, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-
-  // Another zero length copy.
-  ByteArray::Copy(external, 4, b_4_5_6_7, 0);
-  EXPECT_EQ(0, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-
-  // A one element copy.
-  ByteArray::Copy(external, 0, b_4_5_6_7, 1);
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-
-  // A two element copy.
-  ByteArray::Copy(external, 2, b_4_5_6_7, 2);
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(4, external.At(2));
-  EXPECT_EQ(5, external.At(3));
-
-  // A three element copy.
-  ByteArray::Copy(external, 1, b_4_5_6_7, 3);
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(4, external.At(1));
-  EXPECT_EQ(5, external.At(2));
-  EXPECT_EQ(6, external.At(3));
-
-  // A four element copy.
-  ByteArray::Copy(external, 0, b_0_1_2_3, 4);
-  EXPECT_EQ(0, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-}
-
-
-TEST_CASE(Uint8ByteArrayCopyInternalExternal) {
-  const uint8_t b_0_1_2_3[] = { 0, 1, 2, 3 };
-  uint8_t data[] = { 4, 5, 6, 7 };
-
-  const Uint8Array& internal =
-      Uint8Array::Handle(Uint8Array::New(b_0_1_2_3, ARRAY_SIZE(b_0_1_2_3)));
-  EXPECT(!internal.IsNull());
-  EXPECT_EQ(4, internal.Length());
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  const ExternalUint8Array& external =
-      ExternalUint8Array::Handle(
-          ExternalUint8Array::New(data, ARRAY_SIZE(data)));
-  EXPECT(!external.IsNull());
-  EXPECT_EQ(4, external.Length());
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(5, external.At(1));
-  EXPECT_EQ(6, external.At(2));
-  EXPECT_EQ(7, external.At(3));
-
-  // A zero length copy.
-  ByteArray::Copy(internal, 0, external, 0, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A zero length copy, take 2.
-  ByteArray::Copy(internal, 4, external, 0, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A zero length copy, take 3.
-  ByteArray::Copy(internal, 0, external, 4, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A zero length copy, take 4.
-  ByteArray::Copy(internal, 4, external, 4, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A four element copy.
-  ByteArray::Copy(internal, 0, external, 0, 4);
-  EXPECT_EQ(4, internal.At(0));
-  EXPECT_EQ(5, internal.At(1));
-  EXPECT_EQ(6, internal.At(2));
-  EXPECT_EQ(7, internal.At(3));
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(5, external.At(1));
-  EXPECT_EQ(6, external.At(2));
-  EXPECT_EQ(7, external.At(3));
-
-  // A four element copy, take 2.
-  ByteArray::Copy(external, 0, b_0_1_2_3, 4);
-  EXPECT_EQ(0, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-  ByteArray::Copy(external, 0, internal, 0, 4);
-  EXPECT_EQ(4, internal.At(0));
-  EXPECT_EQ(5, internal.At(1));
-  EXPECT_EQ(6, internal.At(2));
-  EXPECT_EQ(7, internal.At(3));
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(5, external.At(1));
-  EXPECT_EQ(6, external.At(2));
-  EXPECT_EQ(7, external.At(3));
-}
-
-
-TEST_CASE(ClampedUint8ByteArrayCopyInternalExternal) {
-  const uint8_t b_0_1_2_3[] = { 0, 1, 2, 3 };
-  uint8_t data[] = { 4, 5, 6, 7 };
-
-  const Uint8ClampedArray& internal =
-      Uint8ClampedArray::Handle(
-          Uint8ClampedArray::New(b_0_1_2_3, ARRAY_SIZE(b_0_1_2_3)));
-  EXPECT(!internal.IsNull());
-  EXPECT_EQ(4, internal.Length());
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  const ExternalUint8ClampedArray& external =
-      ExternalUint8ClampedArray::Handle(
-          ExternalUint8ClampedArray::New(data, ARRAY_SIZE(data)));
-  EXPECT(!external.IsNull());
-  EXPECT_EQ(4, external.Length());
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(5, external.At(1));
-  EXPECT_EQ(6, external.At(2));
-  EXPECT_EQ(7, external.At(3));
-
-  // A zero length copy.
-  ByteArray::Copy(internal, 0, external, 0, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A zero length copy, take 2.
-  ByteArray::Copy(internal, 4, external, 0, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A zero length copy, take 3.
-  ByteArray::Copy(internal, 0, external, 4, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A zero length copy, take 4.
-  ByteArray::Copy(internal, 4, external, 4, 0);
-  EXPECT_EQ(0, internal.At(0));
-  EXPECT_EQ(1, internal.At(1));
-  EXPECT_EQ(2, internal.At(2));
-  EXPECT_EQ(3, internal.At(3));
-
-  // A four element copy.
-  ByteArray::Copy(internal, 0, external, 0, 4);
-  EXPECT_EQ(4, internal.At(0));
-  EXPECT_EQ(5, internal.At(1));
-  EXPECT_EQ(6, internal.At(2));
-  EXPECT_EQ(7, internal.At(3));
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(5, external.At(1));
-  EXPECT_EQ(6, external.At(2));
-  EXPECT_EQ(7, external.At(3));
-
-  // A four element copy, take 2.
-  ByteArray::Copy(external, 0, b_0_1_2_3, 4);
-  EXPECT_EQ(0, external.At(0));
-  EXPECT_EQ(1, external.At(1));
-  EXPECT_EQ(2, external.At(2));
-  EXPECT_EQ(3, external.At(3));
-  ByteArray::Copy(external, 0, internal, 0, 4);
-  EXPECT_EQ(4, internal.At(0));
-  EXPECT_EQ(5, internal.At(1));
-  EXPECT_EQ(6, internal.At(2));
-  EXPECT_EQ(7, internal.At(3));
-  EXPECT_EQ(4, external.At(0));
-  EXPECT_EQ(5, external.At(1));
-  EXPECT_EQ(6, external.At(2));
-  EXPECT_EQ(7, external.At(3));
-}
-
-
 TEST_CASE(Script) {
   const char* url_chars = "builtin:test-case";
   const char* source_chars = "This will not compile.";
diff --git a/runtime/vm/pages.h b/runtime/vm/pages.h
index 69632b6..f3e67a3 100644
--- a/runtime/vm/pages.h
+++ b/runtime/vm/pages.h
@@ -127,8 +127,11 @@
   void EvaluateGarbageCollection(intptr_t in_use_before, intptr_t in_use_after,
                                  int64_t start, int64_t end);
 
-  void Enable() {
-    is_enabled_ = true;
+  void set_is_enabled(bool state) {
+    is_enabled_ = state;
+  }
+  bool is_enabled() {
+    return is_enabled_;
   }
 
  private:
@@ -204,8 +207,12 @@
 
   void StartEndAddress(uword* start, uword* end) const;
 
-  void EnableGrowthControl() {
-    page_space_controller_.Enable();
+  void SetGrowthControlState(bool state) {
+    page_space_controller_.set_is_enabled(state);
+  }
+
+  bool GrowthControlState() {
+    return page_space_controller_.is_enabled();
   }
 
   void WriteProtect(bool read_only);
diff --git a/runtime/vm/parser.cc b/runtime/vm/parser.cc
index 9908873..fa258c4 100644
--- a/runtime/vm/parser.cc
+++ b/runtime/vm/parser.cc
@@ -4197,27 +4197,6 @@
 }
 
 
-// TODO(hausner): Remove support for old library definition syntax.
-void Parser::ParseLibraryNameObsoleteSyntax() {
-  if ((script_.kind() == RawScript::kLibraryTag) &&
-      (CurrentToken() != Token::kLEGACY_LIBRARY)) {
-    // Handle error case early to get consistent error message.
-    ExpectToken(Token::kLEGACY_LIBRARY);
-  }
-  if (CurrentToken() == Token::kLEGACY_LIBRARY) {
-    ConsumeToken();
-    ExpectToken(Token::kLPAREN);
-    if (CurrentToken() != Token::kSTRING) {
-      ErrorMsg("library name expected");
-    }
-    const String& name = *CurrentLiteral();
-    ConsumeToken();
-    ExpectToken(Token::kRPAREN);
-    ExpectToken(Token::kSEMICOLON);
-    library_.SetName(name);
-  }
-}
-
 
 RawObject* Parser::CallLibraryTagHandler(Dart_LibraryTag tag,
                                           intptr_t token_pos,
@@ -4252,91 +4231,6 @@
 }
 
 
-// TODO(hausner): Remove support for old library definition syntax.
-void Parser::ParseLibraryImportObsoleteSyntax() {
-  while (CurrentToken() == Token::kLEGACY_IMPORT) {
-    const intptr_t import_pos = TokenPos();
-    ConsumeToken();
-    ExpectToken(Token::kLPAREN);
-    if (CurrentToken() != Token::kSTRING) {
-      ErrorMsg("library url expected");
-    }
-    const String& url = *CurrentLiteral();
-    ConsumeToken();
-    String& prefix = String::Handle();
-    if (CurrentToken() == Token::kCOMMA) {
-      ConsumeToken();
-      if (!IsLiteral("prefix")) {
-        ErrorMsg("prefix: expected");
-      }
-      ConsumeToken();
-      ExpectToken(Token::kCOLON);
-      if (CurrentToken() != Token::kSTRING) {
-        ErrorMsg("prefix expected");
-      }
-      prefix = CurrentLiteral()->raw();
-      // TODO(asiva): Need to also check that prefix is not a reserved keyword.
-      if (!Scanner::IsIdent(prefix)) {
-        ErrorMsg("prefix should be an identifier");
-      }
-      ConsumeToken();
-    }
-    ExpectToken(Token::kRPAREN);
-    ExpectToken(Token::kSEMICOLON);
-    const String& canon_url = String::CheckedHandle(
-        CallLibraryTagHandler(kCanonicalizeUrl, import_pos, url));
-    // Lookup the library URL.
-    Library& library = Library::Handle(Library::LookupLibrary(canon_url));
-    if (library.IsNull()) {
-      // Call the library tag handler to load the library.
-      CallLibraryTagHandler(kImportTag, import_pos, canon_url);
-      // If the library tag handler succeded without registering the
-      // library we create an empty library to import.
-      library = Library::LookupLibrary(canon_url);
-      if (library.IsNull()) {
-        library = Library::New(canon_url);
-        library.Register();
-      }
-    }
-    // Add the import to the library.
-    const Namespace& import = Namespace::Handle(
-        Namespace::New(library, Array::Handle(), Array::Handle()));
-    if (prefix.IsNull() || (prefix.Length() == 0)) {
-      library_.AddImport(import);
-    } else {
-      LibraryPrefix& library_prefix = LibraryPrefix::Handle();
-      library_prefix = library_.LookupLocalLibraryPrefix(prefix);
-      if (!library_prefix.IsNull()) {
-        library_prefix.AddImport(import);
-      } else {
-        library_prefix = LibraryPrefix::New(prefix, import);
-        library_.AddObject(library_prefix, prefix);
-      }
-    }
-  }
-}
-
-
-// TODO(hausner): Remove support for old library definition syntax.
-void Parser::ParseLibraryIncludeObsoleteSyntax() {
-  while (CurrentToken() == Token::kLEGACY_SOURCE) {
-    const intptr_t source_pos = TokenPos();
-    ConsumeToken();
-    ExpectToken(Token::kLPAREN);
-    if (CurrentToken() != Token::kSTRING) {
-      ErrorMsg("source url expected");
-    }
-    const String& url = *CurrentLiteral();
-    ConsumeToken();
-    ExpectToken(Token::kRPAREN);
-    ExpectToken(Token::kSEMICOLON);
-    const String& canon_url = String::CheckedHandle(
-        CallLibraryTagHandler(kCanonicalizeUrl, source_pos, url));
-    CallLibraryTagHandler(kSourceTag, source_pos, canon_url);
-  }
-}
-
-
 void Parser::ParseLibraryName() {
   ASSERT(CurrentToken() == Token::kLIBRARY);
   ConsumeToken();
@@ -4486,25 +4380,6 @@
     ConsumeToken();
   }
 
-  // TODO(hausner): Remove support for old library definition syntax.
-  if ((CurrentToken() == Token::kLEGACY_LIBRARY) ||
-      (CurrentToken() == Token::kLEGACY_IMPORT) ||
-      (CurrentToken() == Token::kLEGACY_SOURCE)) {
-    ParseLibraryNameObsoleteSyntax();
-    ParseLibraryImportObsoleteSyntax();
-    ParseLibraryIncludeObsoleteSyntax();
-    // Core lib has not been explicitly imported, so we implicitly
-    // import it here.
-    if (!library_.ImportsCorelib()) {
-      Library& core_lib = Library::Handle(Library::CoreLibrary());
-      ASSERT(!core_lib.IsNull());
-      const Namespace& core_ns = Namespace::Handle(
-          Namespace::New(core_lib, Array::Handle(), Array::Handle()));
-      library_.AddImport(core_ns);
-    }
-    return;
-  }
-
   ASSERT(script_.kind() != RawScript::kSourceTag);
 
   // We may read metadata tokens that are part of the toplevel
diff --git a/runtime/vm/raw_object.cc b/runtime/vm/raw_object.cc
index 4c0e66e..130e717 100644
--- a/runtime/vm/raw_object.cc
+++ b/runtime/vm/raw_object.cc
@@ -182,13 +182,6 @@
         instance_size = Uint64Array::InstanceSize(byte_array_length);
         break;
       }
-      case kFloat32x4ArrayCid: {
-        const RawFloat32x4Array* raw_byte_array =
-            reinterpret_cast<const RawFloat32x4Array*>(this);
-        intptr_t byte_array_length = Smi::Value(raw_byte_array->ptr()->length_);
-        instance_size = Float32x4Array::InstanceSize(byte_array_length);
-        break;
-      }
       case kFloat32ArrayCid: {
         const RawFloat32Array* raw_byte_array =
             reinterpret_cast<const RawFloat32Array*>(this);
@@ -321,6 +314,15 @@
         break;
       }
 #undef RAW_VISITPOINTERS
+#define RAW_VISITPOINTERS(clazz)                                               \
+      case kTypedData##clazz##ViewCid:
+      CLASS_LIST_TYPED_DATA(RAW_VISITPOINTERS)
+      case kByteDataViewCid: {
+        RawInstance* raw_obj = reinterpret_cast<RawInstance*>(this);
+        size = RawInstance::VisitInstancePointers(raw_obj, visitor);
+        break;
+      }
+#undef RAW_VISITPOINTERS
       case kFreeListElement: {
         ASSERT(FreeBit::decode(ptr()->tags_));
         uword addr = RawObject::ToAddr(const_cast<RawObject*>(this));
@@ -925,16 +927,6 @@
   return Uint64Array::InstanceSize(length);
 }
 
-
-intptr_t RawFloat32x4Array::VisitFloat32x4ArrayPointers(
-    RawFloat32x4Array *raw_obj, ObjectPointerVisitor* visitor) {
-  // Make sure that we got here with the tagged pointer as this.
-  ASSERT(raw_obj->IsHeapObject());
-  intptr_t length = Smi::Value(raw_obj->ptr()->length_);
-  visitor->VisitPointers(raw_obj->from(), raw_obj->to());
-  return Float32x4Array::InstanceSize(length);
-}
-
 intptr_t RawFloat32Array::VisitFloat32ArrayPointers(
     RawFloat32Array *raw_obj, ObjectPointerVisitor* visitor) {
   // Make sure that we got here with the tagged pointer as this.
@@ -1036,15 +1028,6 @@
 }
 
 
-intptr_t RawExternalFloat32x4Array::VisitExternalFloat32x4ArrayPointers(
-    RawExternalFloat32x4Array* raw_obj, ObjectPointerVisitor* visitor) {
-  // Make sure that we got here with the tagged pointer as this.
-  ASSERT(raw_obj->IsHeapObject());
-  visitor->VisitPointers(raw_obj->from(), raw_obj->to());
-  return ExternalFloat32x4Array::InstanceSize();
-}
-
-
 intptr_t RawExternalFloat32Array::VisitExternalFloat32ArrayPointers(
     RawExternalFloat32Array* raw_obj, ObjectPointerVisitor* visitor) {
   // Make sure that we got here with the tagged pointer as this.
diff --git a/runtime/vm/raw_object.h b/runtime/vm/raw_object.h
index c8cb774..a47d3b1 100644
--- a/runtime/vm/raw_object.h
+++ b/runtime/vm/raw_object.h
@@ -73,7 +73,6 @@
       V(Uint32Array)                                                           \
       V(Int64Array)                                                            \
       V(Uint64Array)                                                           \
-      V(Float32x4Array)                                                        \
       V(Float32Array)                                                          \
       V(Float64Array)                                                          \
       V(ExternalInt8Array)                                                     \
@@ -85,7 +84,6 @@
       V(ExternalUint32Array)                                                   \
       V(ExternalInt64Array)                                                    \
       V(ExternalUint64Array)                                                   \
-      V(ExternalFloat32x4Array)                                                \
       V(ExternalFloat32Array)                                                  \
       V(ExternalFloat64Array)                                                  \
     V(TypedData)                                                               \
@@ -117,6 +115,7 @@
   V(Uint64Array)                                                               \
   V(Float32Array)                                                              \
   V(Float64Array)                                                              \
+  V(Float32x4Array)                                                            \
 
 #define CLASS_LIST_FOR_HANDLES(V)                                              \
   CLASS_LIST_NO_OBJECT_OR_STRING(V)                                            \
@@ -155,6 +154,12 @@
 #undef DEFINE_OBJECT_KIND
 
 #define DEFINE_OBJECT_KIND(clazz)                                              \
+  kTypedData##clazz##ViewCid,
+CLASS_LIST_TYPED_DATA(DEFINE_OBJECT_KIND)
+  kByteDataViewCid,
+#undef DEFINE_OBJECT_KIND
+
+#define DEFINE_OBJECT_KIND(clazz)                                              \
   kExternalTypedData##clazz##Cid,
 CLASS_LIST_TYPED_DATA(DEFINE_OBJECT_KIND)
 #undef DEFINE_OBJECT_KIND
@@ -392,6 +397,7 @@
   static bool IsByteArrayClassId(intptr_t index);
   static bool IsExternalByteArrayClassId(intptr_t index);
   static bool IsTypedDataClassId(intptr_t index);
+  static bool IsTypedDataViewClassId(intptr_t index);
   static bool IsExternalTypedDataClassId(intptr_t index);
 
   static intptr_t NumberOfTypedDataClasses();
@@ -707,7 +713,7 @@
   }
   RawString* private_key_;  // Key used for private identifiers.
   RawArray* token_objects_;
-  RawExternalUint8Array* stream_;
+  RawExternalTypedData* stream_;
   RawObject** to() {
     return reinterpret_cast<RawObject**>(&ptr()->stream_);
   }
@@ -1433,6 +1439,8 @@
 
   // Variable length data follows here.
   uint8_t data_[0];
+
+  friend class Object;
 };
 
 
@@ -1446,6 +1454,9 @@
 
   uint8_t* data_;
   void* peer_;
+
+  friend class TokenStream;
+  friend class RawTokenStream;
 };
 
 
@@ -1464,8 +1475,6 @@
 
   // Variable length data follows here.
   int8_t data_[0];
-
-  friend class Object;
 };
 
 
@@ -1537,13 +1546,6 @@
 };
 
 
-class RawFloat32x4Array : public RawByteArray {
-  RAW_HEAP_OBJECT_IMPLEMENTATION(Float32x4Array);
-
-  // Variable length data follows here.
-  simd128_value_t data_[0];
-};
-
 class RawFloat32Array : public RawByteArray {
   RAW_HEAP_OBJECT_IMPLEMENTATION(Float32Array);
 
@@ -1574,8 +1576,6 @@
   uint8_t* data_;
   void* peer_;
 
-  friend class TokenStream;
-  friend class RawTokenStream;
   friend class RawExternalUint8ClampedArray;
 };
 
@@ -1633,14 +1633,6 @@
 };
 
 
-class RawExternalFloat32x4Array : public RawByteArray {
-  RAW_HEAP_OBJECT_IMPLEMENTATION(ExternalFloat32x4Array);
-
-  simd128_value_t* data_;
-  void* peer_;
-};
-
-
 class RawExternalFloat32Array : public RawByteArray {
   RAW_HEAP_OBJECT_IMPLEMENTATION(ExternalFloat32Array);
 
@@ -1824,22 +1816,20 @@
          kUint32ArrayCid == kByteArrayCid + 7 &&
          kInt64ArrayCid == kByteArrayCid + 8 &&
          kUint64ArrayCid == kByteArrayCid + 9 &&
-         kFloat32x4ArrayCid == kByteArrayCid + 10 &&
-         kFloat32ArrayCid == kByteArrayCid + 11 &&
-         kFloat64ArrayCid == kByteArrayCid + 12 &&
-         kExternalInt8ArrayCid == kByteArrayCid + 13 &&
-         kExternalUint8ArrayCid == kByteArrayCid + 14 &&
-         kExternalUint8ClampedArrayCid == kByteArrayCid + 15 &&
-         kExternalInt16ArrayCid == kByteArrayCid + 16 &&
-         kExternalUint16ArrayCid == kByteArrayCid + 17 &&
-         kExternalInt32ArrayCid == kByteArrayCid + 18 &&
-         kExternalUint32ArrayCid == kByteArrayCid + 19 &&
-         kExternalInt64ArrayCid == kByteArrayCid + 20 &&
-         kExternalUint64ArrayCid == kByteArrayCid + 21 &&
-         kExternalFloat32x4ArrayCid == kByteArrayCid + 22 &&
-         kExternalFloat32ArrayCid == kByteArrayCid + 23 &&
-         kExternalFloat64ArrayCid == kByteArrayCid + 24 &&
-         kTypedDataCid == kByteArrayCid + 25);
+         kFloat32ArrayCid == kByteArrayCid + 10 &&
+         kFloat64ArrayCid == kByteArrayCid + 11 &&
+         kExternalInt8ArrayCid == kByteArrayCid + 12 &&
+         kExternalUint8ArrayCid == kByteArrayCid + 13 &&
+         kExternalUint8ClampedArrayCid == kByteArrayCid + 14 &&
+         kExternalInt16ArrayCid == kByteArrayCid + 15 &&
+         kExternalUint16ArrayCid == kByteArrayCid + 16 &&
+         kExternalInt32ArrayCid == kByteArrayCid + 17 &&
+         kExternalUint32ArrayCid == kByteArrayCid + 18 &&
+         kExternalInt64ArrayCid == kByteArrayCid + 19 &&
+         kExternalUint64ArrayCid == kByteArrayCid + 20 &&
+         kExternalFloat32ArrayCid == kByteArrayCid + 21 &&
+         kExternalFloat64ArrayCid == kByteArrayCid + 22 &&
+         kTypedDataCid == kByteArrayCid + 23);
   return (index >= kByteArrayCid && index <= kExternalFloat64ArrayCid);
 }
 
@@ -1854,10 +1844,9 @@
          kExternalUint32ArrayCid == kExternalInt8ArrayCid + 6 &&
          kExternalInt64ArrayCid == kExternalInt8ArrayCid + 7 &&
          kExternalUint64ArrayCid == kExternalInt8ArrayCid + 8 &&
-         kExternalFloat32x4ArrayCid == kExternalInt8ArrayCid + 9 &&
-         kExternalFloat32ArrayCid == kExternalInt8ArrayCid + 10 &&
-         kExternalFloat64ArrayCid == kExternalInt8ArrayCid + 11 &&
-         kTypedDataCid == kExternalInt8ArrayCid + 12);
+         kExternalFloat32ArrayCid == kExternalInt8ArrayCid + 9 &&
+         kExternalFloat64ArrayCid == kExternalInt8ArrayCid + 10 &&
+         kTypedDataCid == kExternalInt8ArrayCid + 11);
   return (index >= kExternalInt8ArrayCid && index <= kExternalFloat64ArrayCid);
 }
 
@@ -1874,9 +1863,30 @@
          kTypedDataUint64ArrayCid == kTypedDataInt8ArrayCid + 8 &&
          kTypedDataFloat32ArrayCid == kTypedDataInt8ArrayCid + 9 &&
          kTypedDataFloat64ArrayCid == kTypedDataInt8ArrayCid + 10 &&
-         kExternalTypedDataInt8ArrayCid == kTypedDataInt8ArrayCid + 11);
+         kTypedDataFloat32x4ArrayCid == kTypedDataInt8ArrayCid + 11 &&
+         kTypedDataInt8ArrayViewCid == kTypedDataInt8ArrayCid + 12);
   return (index >= kTypedDataInt8ArrayCid &&
-          index <= kTypedDataFloat64ArrayCid);
+          index <= kTypedDataFloat32x4ArrayCid);
+}
+
+
+inline bool RawObject::IsTypedDataViewClassId(intptr_t index) {
+  // Make sure this is updated when new TypedData types are added.
+  ASSERT(kTypedDataUint8ArrayViewCid == kTypedDataInt8ArrayViewCid + 1 &&
+         kTypedDataUint8ClampedArrayViewCid == kTypedDataInt8ArrayViewCid + 2 &&
+         kTypedDataInt16ArrayViewCid == kTypedDataInt8ArrayViewCid + 3 &&
+         kTypedDataUint16ArrayViewCid == kTypedDataInt8ArrayViewCid + 4 &&
+         kTypedDataInt32ArrayViewCid == kTypedDataInt8ArrayViewCid + 5 &&
+         kTypedDataUint32ArrayViewCid == kTypedDataInt8ArrayViewCid + 6 &&
+         kTypedDataInt64ArrayViewCid == kTypedDataInt8ArrayViewCid + 7 &&
+         kTypedDataUint64ArrayViewCid == kTypedDataInt8ArrayViewCid + 8 &&
+         kTypedDataFloat32ArrayViewCid == kTypedDataInt8ArrayViewCid + 9 &&
+         kTypedDataFloat64ArrayViewCid == kTypedDataInt8ArrayViewCid + 10 &&
+         kTypedDataFloat32x4ArrayViewCid == kTypedDataInt8ArrayViewCid + 11 &&
+         kByteDataViewCid == kTypedDataInt8ArrayViewCid + 12 &&
+         kExternalTypedDataInt8ArrayCid == kTypedDataInt8ArrayViewCid + 13);
+  return (index >= kTypedDataInt8ArrayViewCid &&
+          index <= kByteDataViewCid);
 }
 
 
@@ -1902,16 +1912,19 @@
           kExternalTypedDataInt8ArrayCid + 9) &&
          (kExternalTypedDataFloat64ArrayCid ==
           kExternalTypedDataInt8ArrayCid + 10) &&
-         (kNullCid == kExternalTypedDataInt8ArrayCid + 11));
+         (kExternalTypedDataFloat32x4ArrayCid ==
+          kExternalTypedDataInt8ArrayCid + 11) &&
+         (kNullCid == kExternalTypedDataInt8ArrayCid + 12));
   return (index >= kExternalTypedDataInt8ArrayCid &&
-          index <= kExternalTypedDataFloat64ArrayCid);
+          index <= kExternalTypedDataFloat32x4ArrayCid);
 }
 
 
 inline intptr_t RawObject::NumberOfTypedDataClasses() {
   // Make sure this is updated when new TypedData types are added.
-  ASSERT(kExternalTypedDataInt8ArrayCid == kTypedDataInt8ArrayCid + 11);
-  ASSERT(kNullCid == kExternalTypedDataInt8ArrayCid + 11);
+  ASSERT(kTypedDataInt8ArrayViewCid == kTypedDataInt8ArrayCid + 12);
+  ASSERT(kExternalTypedDataInt8ArrayCid == kTypedDataInt8ArrayViewCid + 13);
+  ASSERT(kNullCid == kExternalTypedDataInt8ArrayCid + 12);
   return (kNullCid - kTypedDataInt8ArrayCid);
 }
 
diff --git a/runtime/vm/raw_object_snapshot.cc b/runtime/vm/raw_object_snapshot.cc
index 3974b99..cd08d10 100644
--- a/runtime/vm/raw_object_snapshot.cc
+++ b/runtime/vm/raw_object_snapshot.cc
@@ -205,7 +205,16 @@
   }
 
   // If object needs to be a canonical object, Canonicalize it.
-  if ((kind != Snapshot::kFull) && RawObject::IsCanonical(tags)) {
+  // When reading a full snapshot we don't need to canonicalize the object
+  // as it would already be a canonical object.
+  // When reading a script snapshot we need to canonicalize only those object
+  // references that are objects from the core library (loaded from a
+  // full snapshot). Objects that are only in the script need not be
+  // canonicalized as they are already canonical.
+  // When reading a message snapshot we always have to canonicalize the object.
+  if ((kind != Snapshot::kFull) && RawObject::IsCanonical(tags) &&
+      (RawObject::IsCreatedFromSnapshot(tags) ||
+       (kind == Snapshot::kMessage))) {
     type ^= type.Canonicalize();
   }
 
@@ -458,7 +467,16 @@
   }
 
   // If object needs to be a canonical object, Canonicalize it.
-  if ((kind != Snapshot::kFull) && RawObject::IsCanonical(tags)) {
+  // When reading a full snapshot we don't need to canonicalize the object
+  // as it would already be a canonical object.
+  // When reading a script snapshot we need to canonicalize only those object
+  // references that are objects from the core library (loaded from a
+  // full snapshot). Objects that are only in the script need not be
+  // canonicalized as they are already canonical.
+  // When reading a message snapshot we always have to canonicalize the object.
+  if ((kind != Snapshot::kFull) && RawObject::IsCanonical(tags) &&
+      (RawObject::IsCreatedFromSnapshot(tags) ||
+       (kind == Snapshot::kMessage))) {
     type_arguments ^= type_arguments.Canonicalize();
   }
 
@@ -899,7 +917,7 @@
   // snapshots as we made a copy of token stream.
   if (kind == Snapshot::kScript) {
     NoGCScope no_gc;
-    RawExternalUint8Array* stream = token_stream.GetStream();
+    RawExternalTypedData* stream = token_stream.GetStream();
     reader->ReadBytes(stream->ptr()->data_, len);
   }
 
@@ -929,7 +947,7 @@
   writer->WriteIntptrValue(writer->GetObjectTags(this));
 
   // Write out the length field and the token stream.
-  RawExternalUint8Array* stream = ptr()->stream_;
+  RawExternalTypedData* stream = ptr()->stream_;
   intptr_t len = Smi::Value(stream->ptr()->length_);
   writer->Write<RawObject*>(stream->ptr()->length_);
   writer->WriteBytes(stream->ptr()->data_, len);
@@ -1597,7 +1615,14 @@
   if (kind == Snapshot::kFull) {
     mint = reader->NewMint(value);
   } else {
-    if (RawObject::IsCanonical(tags)) {
+    // When reading a script snapshot we need to canonicalize only those object
+    // references that are objects from the core library (loaded from a
+    // full snapshot). Objects that are only in the script need not be
+    // canonicalized as they are already canonical.
+    // When reading a message snapshot we always have to canonicalize.
+    if (RawObject::IsCanonical(tags) &&
+        (RawObject::IsCreatedFromSnapshot(tags) ||
+         (kind == Snapshot::kMessage))) {
       mint = Mint::NewCanonical(value);
     } else {
       mint = Mint::New(value, HEAP_SPACE(kind));
@@ -1648,7 +1673,16 @@
        BigintOperations::FromHexCString(str, HEAP_SPACE(kind))));
 
   // If it is a canonical constant make it one.
-  if ((kind != Snapshot::kFull) && RawObject::IsCanonical(tags)) {
+  // When reading a full snapshot we don't need to canonicalize the object
+  // as it would already be a canonical object.
+  // When reading a script snapshot we need to canonicalize only those object
+  // references that are objects from the core library (loaded from a
+  // full snapshot). Objects that are only in the script need not be
+  // canonicalized as they are already canonical.
+  // When reading a message snapshot we always have to canonicalize the object.
+  if ((kind != Snapshot::kFull) && RawObject::IsCanonical(tags) &&
+      (RawObject::IsCreatedFromSnapshot(tags) ||
+       (kind == Snapshot::kMessage))) {
     obj ^= obj.Canonicalize();
   }
   reader->AddBackRef(object_id, &obj, kIsDeserialized);
@@ -1715,7 +1749,14 @@
   if (kind == Snapshot::kFull) {
     dbl = reader->NewDouble(value);
   } else {
-    if (RawObject::IsCanonical(tags)) {
+    // When reading a script snapshot we need to canonicalize only those object
+    // references that are objects from the core library (loaded from a
+    // full snapshot). Objects that are only in the script need not be
+    // canonicalized as they are already canonical.
+    // When reading a message snapshot we always have to canonicalize.
+    if (RawObject::IsCanonical(tags) &&
+        (RawObject::IsCreatedFromSnapshot(tags) ||
+         (kind == Snapshot::kMessage))) {
       dbl = Double::NewCanonical(value);
     } else {
       dbl = Double::New(value, HEAP_SPACE(kind));
@@ -2250,32 +2291,6 @@
 BYTEARRAY_TYPE_LIST(BYTEARRAY_READ_FROM)
 #undef BYTEARRAY_READ_FROM
 
-RawFloat32x4Array* Float32x4Array::ReadFrom(SnapshotReader* reader,
-                                                      intptr_t object_id,
-                                                      intptr_t tags,
-                                                      Snapshot::Kind kind) {
-  ASSERT(reader != NULL);
-
-  intptr_t len = reader->ReadSmiValue();
-  Float32x4Array& result = Float32x4Array::ZoneHandle(
-      reader->isolate(), Float32x4Array::New(len, HEAP_SPACE(kind)));
-  reader->AddBackRef(object_id, &result, kIsDeserialized);
-
-  // Set the object tags.
-  result.set_tags(tags);
-
-  // Setup the array elements.
-  simd128_value_t v;
-  for (intptr_t i = 0; i < len; ++i) {
-    v.storage[0] = reader->Read<float>();
-    v.storage[1] = reader->Read<float>();
-    v.storage[2] = reader->Read<float>();
-    v.storage[3] = reader->Read<float>();
-    result.SetAt(i, v);
-  }
-  return result.raw();
-}
-
 
 #define EXTERNALARRAY_READ_FROM(name, lname, type)                             \
 RawExternal##name##Array* External##name##Array::ReadFrom(                     \
@@ -2297,7 +2312,6 @@
 }                                                                              \
 
 BYTEARRAY_TYPE_LIST(EXTERNALARRAY_READ_FROM)
-EXTERNALARRAY_READ_FROM(Float32x4, Float32x4, simd128_value_t)
 #undef EXTERNALARRAY_READ_FROM
 
 
@@ -2353,28 +2367,6 @@
 BYTEARRAY_TYPE_LIST(BYTEARRAY_WRITE_TO)
 #undef BYTEARRAY_WRITE_TO
 
-void RawFloat32x4Array::WriteTo(SnapshotWriter* writer, intptr_t object_id,
-                                     Snapshot::Kind kind) {
-  ASSERT(writer != NULL);
-  RawSmi* length = ptr()->length_;
-  float* data = reinterpret_cast<float*>(&ptr()->data_[0]);
-
-  // Write out the serialization header value for this object.
-  writer->WriteInlinedObjectHeader(object_id);
-
-  // Write out the class and tags information.
-  writer->WriteIndexedObject(kFloat32x4ArrayCid);
-  writer->WriteIntptrValue(writer->GetObjectTags(this));
-
-  // Write out the length field.
-  writer->Write<RawObject*>(length);
-
-  // Write out the array elements as floats.
-  intptr_t len = Smi::Value(length)*4;
-  for (intptr_t i = 0; i < len; i++) {
-    writer->Write(data[i]);
-  }
-}
 
 #define EXTERNALARRAY_WRITE_TO(name, lname, type)                              \
 void RawExternal##name##Array::WriteTo(SnapshotWriter* writer,                 \
@@ -2392,29 +2384,6 @@
 
 BYTEARRAY_TYPE_LIST(EXTERNALARRAY_WRITE_TO)
 #undef BYTEARRAY_WRITE_TO
-void RawExternalFloat32x4Array::WriteTo(SnapshotWriter* writer,
-                                             intptr_t object_id,
-                                             Snapshot::Kind kind) {
-  ASSERT(writer != NULL);
-  RawSmi* length = ptr()->length_;
-  float* data = reinterpret_cast<float*>(&ptr()->data_[0]);
-
-  // Write out the serialization header value for this object.
-  writer->WriteInlinedObjectHeader(object_id);
-
-  // Write out the class and tags information.
-  writer->WriteIndexedObject(kExternalFloat32x4ArrayCid);
-  writer->WriteIntptrValue(writer->GetObjectTags(this));
-
-  // Write out the length field.
-  writer->Write<RawObject*>(length);
-
-  // Write out the array elements as floats.
-  intptr_t len = Smi::Value(length)*4;
-  for (intptr_t i = 0; i < len; i++) {
-    writer->Write(data[i]);
-  }
-}
 
 #undef BYTEARRAY_TYPE_LIST
 
diff --git a/runtime/vm/scanner.cc b/runtime/vm/scanner.cc
index 5c589e0..4600760 100644
--- a/runtime/vm/scanner.cc
+++ b/runtime/vm/scanner.cc
@@ -412,7 +412,7 @@
 }
 
 
-void Scanner::ScanLibraryTag() {
+void Scanner::ScanScriptTag() {
   ReadChar();
   if (c0_ == '!') {
     Recognize(Token::kSCRIPTTAG);
@@ -420,27 +420,11 @@
     // similar to a line comment.
     SkipLine();
     return;
-  }
-  if (!IsLetter(c0_)) {
-    ErrorMsg("Unrecognized library tag");
+  } else {
+    ErrorMsg("unexpected character: '#'");
     SkipLine();
     return;
   }
-  const String& ident = String::Handle(ConsumeIdentChars(false));
-  if (ident.Equals(Symbols::Library())) {
-    current_token_.kind = Token::kLEGACY_LIBRARY;
-    return;
-  }
-  if (ident.Equals(Symbols::Import())) {
-    current_token_.kind = Token::kLEGACY_IMPORT;
-    return;
-  }
-  if (ident.Equals(Symbols::Source())) {
-    current_token_.kind = Token::kLEGACY_SOURCE;
-    return;
-  }
-  ErrorMsg("Unrecognized library token");
-  SkipLine();
 }
 
 
@@ -870,7 +854,7 @@
         break;
 
       case '#':
-        ScanLibraryTag();
+        ScanScriptTag();
         break;
 
       default:
diff --git a/runtime/vm/scanner.h b/runtime/vm/scanner.h
index 5f1f75e..42dc417 100644
--- a/runtime/vm/scanner.h
+++ b/runtime/vm/scanner.h
@@ -199,7 +199,7 @@
   // Reads a number literal.
   void ScanNumber(bool dec_point_seen);
 
-  void ScanLibraryTag();
+  void ScanScriptTag();
 
   static void PrintTokens(const GrowableTokenStream& ts);
 
diff --git a/runtime/vm/simulator_mips.cc b/runtime/vm/simulator_mips.cc
index 1e70e4e..a9bf83d 100644
--- a/runtime/vm/simulator_mips.cc
+++ b/runtime/vm/simulator_mips.cc
@@ -711,8 +711,16 @@
       break;
     }
     case BREAK: {
-      SimulatorDebugger dbg(this);
-      dbg.Stop(instr, "breakpoint");
+      if (instr->BreakCodeField() == Instr::kStopMessageCode) {
+        SimulatorDebugger dbg(this);
+        const char* message = *reinterpret_cast<const char**>(
+            reinterpret_cast<intptr_t>(instr) - Instr::kInstrSize);
+        set_pc(get_pc() + Instr::kInstrSize);
+        dbg.Stop(instr, message);
+      } else {
+        SimulatorDebugger dbg(this);
+        dbg.Stop(instr, "breakpoint");
+      }
       break;
     }
     case DIV: {
diff --git a/runtime/vm/simulator_mips.h b/runtime/vm/simulator_mips.h
index 2407de1..6e6997f 100644
--- a/runtime/vm/simulator_mips.h
+++ b/runtime/vm/simulator_mips.h
@@ -40,6 +40,7 @@
   double get_fregister(FRegister) const;
 
   // Accessor for the pc.
+  void set_pc(int32_t value) { pc_ = value; }
   int32_t get_pc() const { return pc_; }
 
   // Accessors for hi, lo registers.
diff --git a/runtime/vm/snapshot.cc b/runtime/vm/snapshot.cc
index c477c7c..6dbff55 100644
--- a/runtime/vm/snapshot.cc
+++ b/runtime/vm/snapshot.cc
@@ -19,7 +19,7 @@
 namespace dart {
 
 static const int kNumInitialReferencesInFullSnapshot = 160 * KB;
-static const int kNumInitialReferences = 4;
+static const int kNumInitialReferences = 64;
 
 
 static bool IsSingletonClassId(intptr_t class_id) {
@@ -54,6 +54,7 @@
 
 static intptr_t ObjectIdFromClassId(intptr_t class_id) {
   ASSERT((class_id > kIllegalCid) && (class_id < kNumPredefinedCids));
+  ASSERT(!RawObject::IsTypedDataViewClassId(class_id));
   return (class_id + kClassIdsOffset);
 }
 
@@ -159,7 +160,7 @@
       type_arguments_(AbstractTypeArguments::Handle()),
       tokens_(Array::Handle()),
       stream_(TokenStream::Handle()),
-      data_(ExternalUint8Array::Handle()),
+      data_(ExternalTypedData::Handle()),
       error_(UnhandledException::Handle()),
       backward_references_((kind == Snapshot::kFull) ?
                            kNumInitialReferencesInFullSnapshot :
@@ -315,15 +316,20 @@
     CLASS_LIST_NO_OBJECT(SNAPSHOT_READ)
 #undef SNAPSHOT_READ
 #define SNAPSHOT_READ(clazz)                                                   \
-    case kTypedData##clazz##Cid: {                                             \
-      obj_ = TypedData::ReadFrom(this, object_id, tags, kind_);                \
-      break;                                                                   \
-    }                                                                          \
-    case kExternalTypedData##clazz##Cid: {                                     \
-      obj_ = ExternalTypedData::ReadFrom(this, object_id, tags, kind_);        \
-      break;                                                                   \
+    case kTypedData##clazz##Cid:                                               \
+
+    CLASS_LIST_TYPED_DATA(SNAPSHOT_READ) {
+      obj_ = TypedData::ReadFrom(this, object_id, tags, kind_);
+      break;
     }
-    CLASS_LIST_TYPED_DATA(SNAPSHOT_READ)
+#undef SNAPSHOT_READ
+#define SNAPSHOT_READ(clazz)                                                   \
+    case kExternalTypedData##clazz##Cid:                                       \
+
+    CLASS_LIST_TYPED_DATA(SNAPSHOT_READ) {
+      obj_ = ExternalTypedData::ReadFrom(this, object_id, tags, kind_);
+      break;
+    }
 #undef SNAPSHOT_READ
     default: UNREACHABLE(); break;
   }
@@ -432,12 +438,12 @@
   cls_ = Object::token_stream_class();
   stream_ = reinterpret_cast<RawTokenStream*>(
       AllocateUninitialized(cls_, TokenStream::InstanceSize()));
-  cls_ = object_store()->external_uint8_array_class();
+  cls_ = isolate()->class_table()->At(kExternalTypedDataUint8ArrayCid);
   uint8_t* array = const_cast<uint8_t*>(CurrentBufferAddress());
   ASSERT(array != NULL);
   Advance(len);
-  data_ = reinterpret_cast<RawExternalUint8Array*>(
-      AllocateUninitialized(cls_, ExternalUint8Array::InstanceSize()));
+  data_ = reinterpret_cast<RawExternalTypedData*>(
+      AllocateUninitialized(cls_, ExternalTypedData::InstanceSize()));
   data_.SetData(array);
   data_.SetLength(len);
   stream_.SetStream(data_);
@@ -461,7 +467,7 @@
   ASSERT(isolate()->no_gc_scope_depth() != 0);
   if (class_id < kNumPredefinedCids) {
     ASSERT((class_id >= kInstanceCid) &&
-           (class_id <= kExternalTypedDataFloat64ArrayCid));
+           (class_id <= kExternalTypedDataFloat32x4ArrayCid));
     return isolate()->class_table()->At(class_id);
   }
   cls_ = Object::class_class();
@@ -803,15 +809,20 @@
     CLASS_LIST_NO_OBJECT(SNAPSHOT_READ)
 #undef SNAPSHOT_READ
 #define SNAPSHOT_READ(clazz)                                                   \
-    case kTypedData##clazz##Cid: {                                             \
-      obj_ = TypedData::ReadFrom(this, object_id, tags, kind_);                \
-      break;                                                                   \
-    }                                                                          \
-    case kExternalTypedData##clazz##Cid: {                                     \
-      obj_ = ExternalTypedData::ReadFrom(this, object_id, tags, kind_);        \
-      break;                                                                   \
+    case kTypedData##clazz##Cid:                                               \
+
+    CLASS_LIST_TYPED_DATA(SNAPSHOT_READ) {
+      obj_ = TypedData::ReadFrom(this, object_id, tags, kind_);
+      break;
     }
-    CLASS_LIST_TYPED_DATA(SNAPSHOT_READ)
+#undef SNAPSHOT_READ
+#define SNAPSHOT_READ(clazz)                                                   \
+    case kExternalTypedData##clazz##Cid:                                       \
+
+    CLASS_LIST_TYPED_DATA(SNAPSHOT_READ) {
+      obj_ = ExternalTypedData::ReadFrom(this, object_id, tags, kind_);
+      break;
+    }
 #undef SNAPSHOT_READ
     default: UNREACHABLE(); break;
   }
@@ -840,10 +851,10 @@
 
 
 SnapshotWriter::SnapshotWriter(Snapshot::Kind kind,
-               uint8_t** buffer,
-               ReAlloc alloc,
-               intptr_t increment_size)
-    : BaseWriter(buffer, alloc, increment_size),
+                               uint8_t** buffer,
+                               ReAlloc alloc,
+                               intptr_t initial_size)
+    : BaseWriter(buffer, alloc, initial_size),
       kind_(kind),
       object_store_(Isolate::Current()->object_store()),
       class_table_(Isolate::Current()->class_table()),
@@ -926,29 +937,7 @@
   intptr_t class_id = cls->ptr()->id_;
   ASSERT(class_id == raw->GetClassId());
   if (class_id >= kNumPredefinedCids) {
-    if (Class::IsSignatureClass(cls)) {
-      // We do not allow closure objects in an isolate message.
-      set_exception_type(Exceptions::kArgument);
-      // TODO(6726): Allocate these constant strings once in the VM isolate.
-      set_exception_msg("Illegal argument in isolate message"
-                        " : (object is a closure)");
-      Isolate::Current()->long_jump_base()->Jump(1, *ErrorHandle());
-    }
-    // Object is being referenced, add it to the forward ref list and mark
-    // it so that future references to this object in the snapshot will use
-    // this object id. Mark it as not having been serialized yet so that we
-    // will serialize the object when we go through the forward list.
-    intptr_t object_id = MarkObject(raw, kIsNotSerialized);
-
-    // Write out the serialization header value for this object.
-    WriteInlinedObjectHeader(object_id);
-
-    // Indicate this is an instance object.
-    WriteIntptrValue(SerializedHeaderData::encode(kInstanceObjectId));
-
-    // Write out the class information for this object.
-    WriteObjectImpl(cls);
-
+    WriteInstanceRef(raw, cls);
     return;
   }
   if (class_id == kArrayCid) {
@@ -1007,19 +996,32 @@
     CLASS_LIST_NO_OBJECT(SNAPSHOT_WRITE)
 #undef SNAPSHOT_WRITE
 #define SNAPSHOT_WRITE(clazz)                                                  \
-    case kTypedData##clazz##Cid: {                                             \
-      RawTypedData* raw_obj = reinterpret_cast<RawTypedData*>(raw);            \
-      raw_obj->WriteTo(this, object_id, kind_);                                \
-      return;                                                                  \
-    }                                                                          \
-    case kExternalTypedData##clazz##Cid: {                                     \
-      RawExternalTypedData* raw_obj =                                          \
-        reinterpret_cast<RawExternalTypedData*>(raw);                          \
-      raw_obj->WriteTo(this, object_id, kind_);                                \
-      return;                                                                  \
-    }                                                                          \
+    case kTypedData##clazz##Cid:                                               \
+
+    CLASS_LIST_TYPED_DATA(SNAPSHOT_WRITE) {
+      RawTypedData* raw_obj = reinterpret_cast<RawTypedData*>(raw);
+      raw_obj->WriteTo(this, object_id, kind_);
+      return;
+    }
+#undef SNAPSHOT_WRITE
+#define SNAPSHOT_WRITE(clazz)                                                  \
+    case kExternalTypedData##clazz##Cid:                                       \
+
+    CLASS_LIST_TYPED_DATA(SNAPSHOT_WRITE) {
+      RawExternalTypedData* raw_obj =
+        reinterpret_cast<RawExternalTypedData*>(raw);
+      raw_obj->WriteTo(this, object_id, kind_);
+      return;
+    }
+#undef SNAPSHOT_WRITE
+#define SNAPSHOT_WRITE(clazz)                                                  \
+    case kTypedData##clazz##ViewCid:                                           \
 
     CLASS_LIST_TYPED_DATA(SNAPSHOT_WRITE)
+    case kByteDataViewCid: {
+      WriteInstanceRef(raw, cls);
+      return;
+    }
 #undef SNAPSHOT_WRITE
     default: break;
   }
@@ -1198,47 +1200,7 @@
   intptr_t class_id = cls->ptr()->id_;
 
   if (class_id >= kNumPredefinedCids) {
-    if (Class::IsSignatureClass(cls)) {
-      // We do not allow closure objects in an isolate message.
-      set_exception_type(Exceptions::kArgument);
-      // TODO(6726): Allocate these constant strings once in the VM isolate.
-      set_exception_msg("Illegal argument in isolate message"
-                        " : (object is a closure)");
-      Isolate::Current()->long_jump_base()->Jump(1, *ErrorHandle());
-    }
-    if (cls->ptr()->num_native_fields_ != 0) {
-      // We do not allow objects with native fields in an isolate message.
-      set_exception_type(Exceptions::kArgument);
-      // TODO(6726): Allocate these constant strings once in the VM isolate.
-      set_exception_msg("Illegal argument in isolate message"
-                        " : (object extends NativeWrapper)");
-
-      Isolate::Current()->long_jump_base()->Jump(1, *ErrorHandle());
-    }
-    // Object is regular dart instance.
-    intptr_t instance_size =
-        cls->ptr()->instance_size_in_words_ << kWordSizeLog2;
-    ASSERT(instance_size != 0);
-
-    // Write out the serialization header value for this object.
-    WriteInlinedObjectHeader(object_id);
-
-    // Indicate this is an instance object.
-    WriteIntptrValue(SerializedHeaderData::encode(kInstanceObjectId));
-
-    // Write out the tags.
-    WriteIntptrValue(tags);
-
-    // Write out the class information for this object.
-    WriteObjectImpl(cls);
-
-    // Write out all the fields for the object.
-    intptr_t offset = Object::InstanceSize();
-    while (offset < instance_size) {
-      WriteObjectRef(*reinterpret_cast<RawObject**>(
-          reinterpret_cast<uword>(raw->ptr()) + offset));
-      offset += kWordSize;
-    }
+    WriteInstance(object_id, raw, cls, tags);
     return;
   }
   switch (class_id) {
@@ -1252,19 +1214,32 @@
     CLASS_LIST_NO_OBJECT(SNAPSHOT_WRITE)
 #undef SNAPSHOT_WRITE
 #define SNAPSHOT_WRITE(clazz)                                                  \
-    case kTypedData##clazz##Cid: {                                             \
-      RawTypedData* raw_obj = reinterpret_cast<RawTypedData*>(raw);            \
-      raw_obj->WriteTo(this, object_id, kind_);                                \
-      return;                                                                  \
-    }                                                                          \
-    case kExternalTypedData##clazz##Cid: {                                     \
-      RawExternalTypedData* raw_obj =                                          \
-        reinterpret_cast<RawExternalTypedData*>(raw);                          \
-      raw_obj->WriteTo(this, object_id, kind_);                                \
-      return;                                                                  \
-    }                                                                          \
+    case kTypedData##clazz##Cid:                                               \
+
+    CLASS_LIST_TYPED_DATA(SNAPSHOT_WRITE) {
+      RawTypedData* raw_obj = reinterpret_cast<RawTypedData*>(raw);
+      raw_obj->WriteTo(this, object_id, kind_);
+      return;
+    }
+#undef SNAPSHOT_WRITE
+#define SNAPSHOT_WRITE(clazz)                                                  \
+    case kExternalTypedData##clazz##Cid:                                       \
+
+    CLASS_LIST_TYPED_DATA(SNAPSHOT_WRITE) {
+      RawExternalTypedData* raw_obj =
+        reinterpret_cast<RawExternalTypedData*>(raw);
+      raw_obj->WriteTo(this, object_id, kind_);
+      return;
+    }
+#undef SNAPSHOT_WRITE
+#define SNAPSHOT_WRITE(clazz)                                                  \
+    case kTypedData##clazz##ViewCid:                                           \
 
     CLASS_LIST_TYPED_DATA(SNAPSHOT_WRITE)
+    case kByteDataViewCid: {
+      WriteInstance(object_id, raw, cls, tags);
+      return;
+    }
 #undef SNAPSHOT_WRITE
     default: break;
   }
@@ -1344,6 +1319,83 @@
 }
 
 
+void SnapshotWriter::CheckIfSerializable(RawClass* cls) {
+  if (Class::IsSignatureClass(cls)) {
+    // We do not allow closure objects in an isolate message.
+    set_exception_type(Exceptions::kArgument);
+    // TODO(6726): Allocate these constant strings once in the VM isolate.
+    set_exception_msg("Illegal argument in isolate message"
+                      " : (object is a closure)");
+    Isolate::Current()->long_jump_base()->Jump(1, *ErrorHandle());
+  }
+  if (cls->ptr()->num_native_fields_ != 0) {
+    // We do not allow objects with native fields in an isolate message.
+    set_exception_type(Exceptions::kArgument);
+    // TODO(6726): Allocate these constant strings once in the VM isolate.
+    set_exception_msg("Illegal argument in isolate message"
+                      " : (object extends NativeWrapper)");
+
+    Isolate::Current()->long_jump_base()->Jump(1, *ErrorHandle());
+  }
+}
+
+
+void SnapshotWriter::WriteInstance(intptr_t object_id,
+                                   RawObject* raw,
+                                   RawClass* cls,
+                                   intptr_t tags) {
+  // First check if object is a closure or has native fields.
+  CheckIfSerializable(cls);
+
+  // Object is regular dart instance.
+  intptr_t instance_size =
+      cls->ptr()->instance_size_in_words_ << kWordSizeLog2;
+  ASSERT(instance_size != 0);
+
+  // Write out the serialization header value for this object.
+  WriteInlinedObjectHeader(object_id);
+
+  // Indicate this is an instance object.
+  WriteIntptrValue(SerializedHeaderData::encode(kInstanceObjectId));
+
+  // Write out the tags.
+  WriteIntptrValue(tags);
+
+  // Write out the class information for this object.
+  WriteObjectImpl(cls);
+
+  // Write out all the fields for the object.
+  intptr_t offset = Object::InstanceSize();
+  while (offset < instance_size) {
+    WriteObjectRef(*reinterpret_cast<RawObject**>(
+        reinterpret_cast<uword>(raw->ptr()) + offset));
+    offset += kWordSize;
+  }
+  return;
+}
+
+
+void SnapshotWriter::WriteInstanceRef(RawObject* raw, RawClass* cls) {
+  // First check if object is a closure or has native fields.
+  CheckIfSerializable(cls);
+
+  // Object is being referenced, add it to the forward ref list and mark
+  // it so that future references to this object in the snapshot will use
+  // this object id. Mark it as not having been serialized yet so that we
+  // will serialize the object when we go through the forward list.
+  intptr_t object_id = MarkObject(raw, kIsNotSerialized);
+
+  // Write out the serialization header value for this object.
+  WriteInlinedObjectHeader(object_id);
+
+  // Indicate this is an instance object.
+  WriteIntptrValue(SerializedHeaderData::encode(kInstanceObjectId));
+
+  // Write out the class information for this object.
+  WriteObjectImpl(cls);
+}
+
+
 void SnapshotWriter::ThrowException(Exceptions::ExceptionType type,
                                     const char* msg) {
   Isolate::Current()->object_store()->clear_sticky_error();
diff --git a/runtime/vm/snapshot.h b/runtime/vm/snapshot.h
index 5d199f6..de87940 100644
--- a/runtime/vm/snapshot.h
+++ b/runtime/vm/snapshot.h
@@ -23,7 +23,7 @@
 class Array;
 class Class;
 class ClassTable;
-class ExternalUint8Array;
+class ExternalTypedData;
 class GrowableObjectArray;
 class Heap;
 class LanguageError;
@@ -225,7 +225,7 @@
   AbstractTypeArguments* TypeArgumentsHandle() { return &type_arguments_; }
   Array* TokensHandle() { return &tokens_; }
   TokenStream* StreamHandle() { return &stream_; }
-  ExternalUint8Array* DataHandle() { return &data_; }
+  ExternalTypedData* DataHandle() { return &data_; }
   UnhandledException* ErrorHandle() { return &error_; }
 
   // Reads an object.
@@ -326,7 +326,7 @@
   AbstractTypeArguments& type_arguments_;  // Temporary type argument handle.
   Array& tokens_;  // Temporary tokens handle.
   TokenStream& stream_;  // Temporary token stream handle.
-  ExternalUint8Array& data_;  // Temporary stream data handle.
+  ExternalTypedData& data_;  // Temporary stream data handle.
   UnhandledException& error_;  // Error handle.
   GrowableArray<BackRefNode*> backward_references_;
 
@@ -416,7 +416,7 @@
  protected:
   BaseWriter(uint8_t** buffer,
              ReAlloc alloc,
-             intptr_t increment_size) : stream_(buffer, alloc, increment_size) {
+             intptr_t initial_size) : stream_(buffer, alloc, initial_size) {
     ASSERT(buffer != NULL);
     ASSERT(alloc != NULL);
   }
@@ -445,7 +445,7 @@
   SnapshotWriter(Snapshot::Kind kind,
                  uint8_t** buffer,
                  ReAlloc alloc,
-                 intptr_t increment_size);
+                 intptr_t initial_size);
 
  public:
   // Snapshot kind.
@@ -504,6 +504,12 @@
                     RawSmi* length,
                     RawAbstractTypeArguments* type_arguments,
                     RawObject* data[]);
+  void CheckIfSerializable(RawClass* cls);
+  void WriteInstance(intptr_t object_id,
+                     RawObject* raw,
+                     RawClass* cls,
+                     intptr_t tags);
+  void WriteInstanceRef(RawObject* raw, RawClass* cls);
 
   ObjectStore* object_store() const { return object_store_; }
 
@@ -534,9 +540,9 @@
 
 class FullSnapshotWriter : public SnapshotWriter {
  public:
-  static const intptr_t kIncrementSize = 64 * KB;
+  static const intptr_t kInitialSize = 64 * KB;
   FullSnapshotWriter(uint8_t** buffer, ReAlloc alloc)
-      : SnapshotWriter(Snapshot::kFull, buffer, alloc, kIncrementSize) {
+      : SnapshotWriter(Snapshot::kFull, buffer, alloc, kInitialSize) {
     ASSERT(buffer != NULL);
     ASSERT(alloc != NULL);
   }
@@ -552,9 +558,9 @@
 
 class ScriptSnapshotWriter : public SnapshotWriter {
  public:
-  static const intptr_t kIncrementSize = 64 * KB;
+  static const intptr_t kInitialSize = 64 * KB;
   ScriptSnapshotWriter(uint8_t** buffer, ReAlloc alloc)
-      : SnapshotWriter(Snapshot::kScript, buffer, alloc, kIncrementSize) {
+      : SnapshotWriter(Snapshot::kScript, buffer, alloc, kInitialSize) {
     ASSERT(buffer != NULL);
     ASSERT(alloc != NULL);
   }
@@ -570,9 +576,9 @@
 
 class MessageWriter : public SnapshotWriter {
  public:
-  static const intptr_t kIncrementSize = 512;
+  static const intptr_t kInitialSize = 512;
   MessageWriter(uint8_t** buffer, ReAlloc alloc)
-      : SnapshotWriter(Snapshot::kMessage, buffer, alloc, kIncrementSize) {
+      : SnapshotWriter(Snapshot::kMessage, buffer, alloc, kInitialSize) {
     ASSERT(buffer != NULL);
     ASSERT(alloc != NULL);
   }
diff --git a/runtime/vm/snapshot_test.cc b/runtime/vm/snapshot_test.cc
index 021569c..08b2ab8 100644
--- a/runtime/vm/snapshot_test.cc
+++ b/runtime/vm/snapshot_test.cc
@@ -647,18 +647,21 @@
     uint8_t* buffer;                                                          \
     MessageWriter writer(&buffer, &zone_allocator);                           \
     const int kArrayLength = 127;                                             \
-    darttype& array = darttype::Handle(darttype::New(kArrayLength));          \
+    TypedData& array = TypedData::Handle(                                     \
+        TypedData::New(kTypedData##darttype##ArrayCid, kArrayLength));        \
+    intptr_t scale = array.ElementSizeInBytes();                              \
     for (int i = 0; i < kArrayLength; i++) {                                  \
-      array.SetAt(i, i);                                                      \
+      array.Set##darttype((i * scale), i);                                    \
     }                                                                         \
     writer.WriteMessage(array);                                               \
     intptr_t buffer_len = writer.BytesWritten();                              \
     SnapshotReader reader(buffer, buffer_len,                                 \
                           Snapshot::kMessage, Isolate::Current());            \
-    darttype& serialized_array = darttype::Handle();                          \
+    TypedData& serialized_array = TypedData::Handle();                        \
     serialized_array ^= reader.ReadObject();                                  \
     for (int i = 0; i < kArrayLength; i++) {                                  \
-      EXPECT_EQ(static_cast<ctype>(i), serialized_array.At(i));               \
+      EXPECT_EQ(static_cast<ctype>(i),                                        \
+                serialized_array.Get##darttype(i*scale));                     \
     }                                                                         \
   }
 
@@ -668,47 +671,50 @@
     StackZone zone(Isolate::Current());                                       \
     ctype data[] = { 0, 11, 22, 33, 44, 55, 66, 77 };                         \
     intptr_t length = ARRAY_SIZE(data);                                       \
-    External##darttype& array = External##darttype::Handle(                   \
-        External##darttype::New(data, length));                               \
+    ExternalTypedData& array = ExternalTypedData::Handle(                     \
+        ExternalTypedData::New(kExternalTypedData##darttype##ArrayCid,        \
+                               reinterpret_cast<uint8_t*>(data), length));    \
+    intptr_t scale = array.ElementSizeInBytes();                              \
     uint8_t* buffer;                                                          \
     MessageWriter writer(&buffer, &zone_allocator);                           \
     writer.WriteMessage(array);                                               \
     intptr_t buffer_len = writer.BytesWritten();                              \
     SnapshotReader reader(buffer, buffer_len,                                 \
                           Snapshot::kMessage, Isolate::Current());            \
-    darttype& serialized_array = darttype::Handle();                          \
+    TypedData& serialized_array = TypedData::Handle();                        \
     serialized_array ^= reader.ReadObject();                                  \
     for (int i = 0; i < length; i++) {                                        \
-      EXPECT_EQ(static_cast<ctype>(data[i]), serialized_array.At(i));         \
+      EXPECT_EQ(static_cast<ctype>(data[i]),                                  \
+                serialized_array.Get##darttype(i*scale));                     \
     }                                                                         \
   }
 
 
 TEST_CASE(SerializeTypedArray) {
-  TEST_TYPED_ARRAY(Int8Array, int8_t);
-  TEST_TYPED_ARRAY(Uint8Array, uint8_t);
-  TEST_TYPED_ARRAY(Int16Array, int16_t);
-  TEST_TYPED_ARRAY(Uint16Array, uint16_t);
-  TEST_TYPED_ARRAY(Int32Array, int32_t);
-  TEST_TYPED_ARRAY(Uint32Array, uint32_t);
-  TEST_TYPED_ARRAY(Int64Array, int64_t);
-  TEST_TYPED_ARRAY(Uint64Array, uint64_t);
-  TEST_TYPED_ARRAY(Float32Array, float);
-  TEST_TYPED_ARRAY(Float64Array, double);
+  TEST_TYPED_ARRAY(Int8, int8_t);
+  TEST_TYPED_ARRAY(Uint8, uint8_t);
+  TEST_TYPED_ARRAY(Int16, int16_t);
+  TEST_TYPED_ARRAY(Uint16, uint16_t);
+  TEST_TYPED_ARRAY(Int32, int32_t);
+  TEST_TYPED_ARRAY(Uint32, uint32_t);
+  TEST_TYPED_ARRAY(Int64, int64_t);
+  TEST_TYPED_ARRAY(Uint64, uint64_t);
+  TEST_TYPED_ARRAY(Float32, float);
+  TEST_TYPED_ARRAY(Float64, double);
 }
 
 
 TEST_CASE(SerializeExternalTypedArray) {
-  TEST_EXTERNAL_TYPED_ARRAY(Int8Array, int8_t);
-  TEST_EXTERNAL_TYPED_ARRAY(Uint8Array, uint8_t);
-  TEST_EXTERNAL_TYPED_ARRAY(Int16Array, int16_t);
-  TEST_EXTERNAL_TYPED_ARRAY(Uint16Array, uint16_t);
-  TEST_EXTERNAL_TYPED_ARRAY(Int32Array, int32_t);
-  TEST_EXTERNAL_TYPED_ARRAY(Uint32Array, uint32_t);
-  TEST_EXTERNAL_TYPED_ARRAY(Int64Array, int64_t);
-  TEST_EXTERNAL_TYPED_ARRAY(Uint64Array, uint64_t);
-  TEST_EXTERNAL_TYPED_ARRAY(Float32Array, float);
-  TEST_EXTERNAL_TYPED_ARRAY(Float64Array, double);
+  TEST_EXTERNAL_TYPED_ARRAY(Int8, int8_t);
+  TEST_EXTERNAL_TYPED_ARRAY(Uint8, uint8_t);
+  TEST_EXTERNAL_TYPED_ARRAY(Int16, int16_t);
+  TEST_EXTERNAL_TYPED_ARRAY(Uint16, uint16_t);
+  TEST_EXTERNAL_TYPED_ARRAY(Int32, int32_t);
+  TEST_EXTERNAL_TYPED_ARRAY(Uint32, uint32_t);
+  TEST_EXTERNAL_TYPED_ARRAY(Int64, int64_t);
+  TEST_EXTERNAL_TYPED_ARRAY(Uint64, uint64_t);
+  TEST_EXTERNAL_TYPED_ARRAY(Float32, float);
+  TEST_EXTERNAL_TYPED_ARRAY(Float64, double);
 }
 
 
@@ -744,9 +750,9 @@
 
 class TestSnapshotWriter : public SnapshotWriter {
  public:
-  static const intptr_t kIncrementSize = 64 * KB;
+  static const intptr_t kInitialSize = 64 * KB;
   TestSnapshotWriter(uint8_t** buffer, ReAlloc alloc)
-      : SnapshotWriter(Snapshot::kScript, buffer, alloc, kIncrementSize) {
+      : SnapshotWriter(Snapshot::kScript, buffer, alloc, kInitialSize) {
     ASSERT(buffer != NULL);
     ASSERT(alloc != NULL);
   }
@@ -835,10 +841,10 @@
   const TokenStream& expected_tokens = TokenStream::Handle(script.tokens());
   const TokenStream& serialized_tokens =
       TokenStream::Handle(serialized_script.tokens());
-  const ExternalUint8Array& expected_data =
-      ExternalUint8Array::Handle(expected_tokens.GetStream());
-  const ExternalUint8Array& serialized_data =
-      ExternalUint8Array::Handle(serialized_tokens.GetStream());
+  const ExternalTypedData& expected_data =
+      ExternalTypedData::Handle(expected_tokens.GetStream());
+  const ExternalTypedData& serialized_data =
+      ExternalTypedData::Handle(serialized_tokens.GetStream());
   EXPECT_EQ(expected_data.Length(), serialized_data.Length());
   TokenStream::Iterator expected_iterator(expected_tokens, 0);
   TokenStream::Iterator serialized_iterator(serialized_tokens, 0);
diff --git a/runtime/vm/stub_code.cc b/runtime/vm/stub_code.cc
index 8160cfb..4e0b075 100644
--- a/runtime/vm/stub_code.cc
+++ b/runtime/vm/stub_code.cc
@@ -50,26 +50,16 @@
 
 
 void StubCode::InitOnce() {
-  // TODO(regis): Re-enable this after we are able to generate mips code.
-#if defined(TARGET_ARCH_IA32) ||                                               \
-    defined(TARGET_ARCH_X64) ||                                                \
-    defined(TARGET_ARCH_ARM)
   // Generate all the stubs.
   Code& code = Code::Handle();
   VM_STUB_CODE_LIST(STUB_CODE_GENERATE);
-#endif
 }
 
 
 void StubCode::GenerateFor(Isolate* init) {
-  // TODO(regis): Re-enable this after we are able to generate mips code.
-#if defined(TARGET_ARCH_IA32) ||                                               \
-    defined(TARGET_ARCH_X64) ||                                                \
-    defined(TARGET_ARCH_ARM)
   // Generate all the stubs.
   Code& code = Code::Handle();
   STUB_CODE_LIST(STUB_CODE_GENERATE);
-#endif
 }
 
 #undef STUB_CODE_GENERATE
diff --git a/runtime/vm/symbols.h b/runtime/vm/symbols.h
index 7a7d9ae..afc5eac 100644
--- a/runtime/vm/symbols.h
+++ b/runtime/vm/symbols.h
@@ -163,6 +163,18 @@
   V(_Float32x4Array, "_Float32x4Array")                                        \
   V(_Float32Array, "_Float32Array")                                            \
   V(_Float64Array, "_Float64Array")                                            \
+  V(_Int8ArrayView, "_Int8ArrayView")                                          \
+  V(_Uint8ArrayView, "_Uint8ArrayView")                                        \
+  V(_Uint8ClampedArrayView, "_Uint8ClampedArrayView")                          \
+  V(_Int16ArrayView, "_Int16ArrayView")                                        \
+  V(_Uint16ArrayView, "_Uint16ArrayView")                                      \
+  V(_Int32ArrayView, "_Int32ArrayView")                                        \
+  V(_Uint32ArrayView, "_Uint32ArrayView")                                      \
+  V(_Int64ArrayView, "_Int64ArrayView")                                        \
+  V(_Uint64ArrayView, "_Uint64ArrayView")                                      \
+  V(_Float32ArrayView, "_Float32ArrayView")                                    \
+  V(_Float64ArrayView, "_Float64ArrayView")                                    \
+  V(_Float32x4ArrayView, "_Float32x4ArrayView")                                \
   V(_ExternalInt8Array, "_ExternalInt8Array")                                  \
   V(_ExternalUint8Array, "_ExternalUint8Array")                                \
   V(_ExternalUint8ClampedArray, "_ExternalUint8ClampedArray")                  \
diff --git a/runtime/vm/token.h b/runtime/vm/token.h
index aebd94a..daf8cea 100644
--- a/runtime/vm/token.h
+++ b/runtime/vm/token.h
@@ -134,9 +134,6 @@
                                                                                \
   /* Support for Dart scripts. */                                              \
   TOK(kSCRIPTTAG, "#!", 0, kNoAttribute)                                       \
-  TOK(kLEGACY_LIBRARY, "#library", 0, kNoAttribute)                            \
-  TOK(kLEGACY_IMPORT, "#import", 0, kNoAttribute)                              \
-  TOK(kLEGACY_SOURCE, "#source", 0, kNoAttribute)                              \
 
 // List of keywords. The list must be alphabetically ordered. The
 // keyword recognition code depends on the ordering.
@@ -293,6 +290,24 @@
   static bool IsBinaryOperator(Token::Kind token);
   static bool IsPrefixOperator(Token::Kind token);
 
+  // For a comparison operation return an operation for the negated comparison:
+  // !(a (op) b) === a (op') b
+  static Token::Kind NegateComparison(Token::Kind op) {
+    switch (op) {
+      case Token::kEQ: return Token::kNE;
+      case Token::kNE: return Token::kEQ;
+      case Token::kLT: return Token::kGTE;
+      case Token::kGT: return Token::kLTE;
+      case Token::kLTE: return Token::kGT;
+      case Token::kGTE: return Token::kLT;
+      case Token::kEQ_STRICT: return Token::kNE_STRICT;
+      case Token::kNE_STRICT: return Token::kEQ_STRICT;
+      default:
+        UNREACHABLE();
+        return Token::kILLEGAL;
+    }
+  }
+
  private:
   static const char* name_[];
   static const char* tok_str_[];
diff --git a/runtime/vm/unit_test.h b/runtime/vm/unit_test.h
index 31c307f..392b69b 100644
--- a/runtime/vm/unit_test.h
+++ b/runtime/vm/unit_test.h
@@ -360,6 +360,22 @@
     }                                                                          \
   } while (0)
 
+#define EXPECT_TRUE(handle)                                                    \
+  do {                                                                         \
+    Dart_Handle tmp_handle = (handle);                                         \
+    if (Dart_IsBoolean(tmp_handle)) {                                          \
+      bool value;                                                              \
+      Dart_BooleanValue(tmp_handle, &value);                                   \
+      if (!value) {                                                            \
+        dart::Expect(__FILE__, __LINE__).Fail("expected True, but was '%s'\n", \
+            #handle);                                                          \
+      }                                                                        \
+    } else {                                                                   \
+      dart::Expect(__FILE__, __LINE__).Fail("expected True, but was '%s'\n",   \
+          #handle);                                                            \
+    }                                                                          \
+  } while (0)
+
 }  // namespace dart
 
 #endif  // VM_UNIT_TEST_H_
diff --git a/sdk/bin/dart2js.bat b/sdk/bin/dart2js.bat
index 4aa849d..97bf774 100644
--- a/sdk/bin/dart2js.bat
+++ b/sdk/bin/dart2js.bat
@@ -3,14 +3,51 @@
 REM for details. All rights reserved. Use of this source code is governed by a
 REM BSD-style license that can be found in the LICENSE file.
 
-set SCRIPTPATH=%~dp0
+setlocal
+rem Handle the case where dart-sdk/bin has been symlinked to.
+set DIR_NAME_WITH_SLASH=%~dp0
+set DIR_NAME=%DIR_NAME_WITH_SLASH:~0,-1%%
+call :follow_links "%DIR_NAME%", RETURNED_BIN_DIR
+rem Get rid of surrounding quotes.
+for %%i in ("%RETURNED_BIN_DIR%") do set BIN_DIR=%%~fi
 
-REM Does the path have a trailing slash? If so, remove it.
-if %SCRIPTPATH:~-1%== set SCRIPTPATH=%SCRIPTPATH:~0,-1%
+rem Get absolute full name for SDK_DIR.
+for %%i in ("%BIN_DIR%\..\") do set SDK_DIR=%%~fi
 
-set arguments=%*
-set SCRIPTNAME="%SCRIPTPATH%..\lib\_internal\compiler\implementation\dart2js.dart"
-set SNAPSHOTNAME="%SCRIPTPATH%dart2js.snapshot"
-if exist %SNAPSHOTNAME% set SCRIPTNAME=%SNAPSHOTNAME%
+set DART2JS=%SDK_DIR%lib\_internal\compiler\implementation\dart2js.dart
+set DART=%BIN_DIR%\dart
+set SNAPSHOT=%DART2JS%.snapshot
 
-"%SCRIPTPATH%dart" --heap_growth_rate=512 %SCRIPTNAME% %arguments%
+set EXTRA_OPTIONS=
+set EXTRA_VM_OPTIONS=
+
+if _%DART2JS_DEVELOPER_MODE%_ == _1_ (
+  set EXTRA_VM_OPTIONS=%EXTRA_VM_OPTIONS% --checked
+)
+
+if exist "%SNAPSHOT%" (
+  echo Using snapshot "%SNAPSHOT%" >&2
+  set DART2JS=%SNAPSHOT%
+)
+
+rem See comments regarding options below in dart2js shell script.
+set EXTRA_VM_OPTIONS=%EXTRA_VM_OPTIONS% --heap_growth_rate=512
+
+"%DART%" %EXTRA_VM_OPTIONS% "%DART2JS%" %EXTRA_OPTIONS% %*
+endlocal
+
+exit /b %errorlevel%
+
+:follow_links
+setlocal
+for %%i in (%1) do set result=%%~fi
+set current=
+for /f "tokens=2 delims=[]" %%i in ('dir /a:l ^"%~dp1^" 2^>nul ^
+                                     ^| find ">     %~n1 ["') do (
+  set current=%%i
+)
+if not "%current%"=="" call :follow_links "%current%", result
+endlocal & set %~2=%result%
+goto :eof
+
+:end
diff --git a/sdk/bin/dart2js_developer.bat b/sdk/bin/dart2js_developer.bat
index fa07652..97ab204 100644
--- a/sdk/bin/dart2js_developer.bat
+++ b/sdk/bin/dart2js_developer.bat
@@ -3,13 +3,7 @@
 REM for details. All rights reserved. Use of this source code is governed by a
 REM BSD-style license that can be found in the LICENSE file.
 
-set SCRIPTPATH=%~dp0
-
-REM Does the path have a trailing slash? If so, remove it.
-if %SCRIPTPATH:~-1%== set SCRIPTPATH=%SCRIPTPATH:~0,-1%
-
-set arguments=%*
-set SNAPSHOTNAME=%SCRIPTPATH%dart2js.snapshot
-if exist %SNAPSHOTNAME% set SNAPSHOT=--use_script_snapshot=%SNAPSHOTNAME%
-
-"%SCRIPTPATH%dart" --checked --heap_growth_rate=512 %SNAPSHOT% "%SCRIPTPATH%..\lib\_internal\compiler\implementation\dart2js.dart" %arguments%
+setlocal
+set DART2JS_DEVELOPER_MODE=1
+call "%~dp0dart2js.bat" %*
+endlocal
\ No newline at end of file
diff --git a/sdk/bin/dartdoc b/sdk/bin/dartdoc
index ed265f7..faec172 100755
--- a/sdk/bin/dartdoc
+++ b/sdk/bin/dartdoc
@@ -23,4 +23,4 @@
   echo Using snapshot "$BIN_DIR/../lib/_internal/dartdoc/bin/dartdoc.dart.snapshot" 1>&2
   SNAPSHOT="--use-script-snapshot=$BIN_DIR/../lib/_internal/dartdoc/bin/dartdoc.dart.snapshot"
 fi
-exec "$BIN_DIR"/dart --heap_growth_rate=32 $SNAPSHOT "$BIN_DIR/../lib/_internal/dartdoc/bin/dartdoc.dart" $COLORS "$@"
+exec "$BIN_DIR"/dart --heap_growth_rate=32 "--package-root=$BIN_DIR/../packages/" $SNAPSHOT "$BIN_DIR/../lib/_internal/dartdoc/bin/dartdoc.dart" $COLORS "$@"
diff --git a/sdk/bin/dartdoc.bat b/sdk/bin/dartdoc.bat
index 98622eb..11911ef 100644
--- a/sdk/bin/dartdoc.bat
+++ b/sdk/bin/dartdoc.bat
@@ -12,4 +12,6 @@
 rem set SNAPSHOTNAME="%SCRIPTPATH%dartdoc.snapshot"
 rem if exist %SNAPSHOTNAME% set SNAPSHOT=--use-script-snapshot=%SNAPSHOTNAME%
 
-"%SCRIPTPATH%dart" --heap_growth_rate=32 %SNAPSHOT% "%SCRIPTPATH%..\lib\_internal\dartdoc\bin\dartdoc.dart" %arguments%
+:: The trailing forward slash in --package-root is required because of issue
+:: 9499.
+"%SCRIPTPATH%dart" --heap_growth_rate=32 "--package-root=%SCRIPTPATH%..\packages/" %SNAPSHOT% "%SCRIPTPATH%..\lib\_internal\dartdoc\bin\dartdoc.dart" %arguments%
diff --git a/sdk/lib/_internal/compiler/implementation/compile_time_constants.dart b/sdk/lib/_internal/compiler/implementation/compile_time_constants.dart
index ca8e7b4..9c134be 100644
--- a/sdk/lib/_internal/compiler/implementation/compile_time_constants.dart
+++ b/sdk/lib/_internal/compiler/implementation/compile_time_constants.dart
@@ -340,7 +340,7 @@
          link = link.tail) {
       arguments.add(evaluateConstant(link.head));
     }
-    // TODO(floitsch): get type parameters.
+    // TODO(9476): get type parameters.
     compiler.listClass.computeType(compiler);
     DartType type = compiler.listClass.rawType;
     Constant constant = new ListConstant(type, arguments);
@@ -377,7 +377,7 @@
       }
     }
     bool hasProtoKey = (protoValue != null);
-    // TODO(floitsch): this should be a List<String> type.
+    // TODO(9476): this should be a List<String> type.
     compiler.listClass.computeType(compiler);
     DartType keysType = compiler.listClass.rawType;
     ListConstant keysList = new ListConstant(keysType, keys);
@@ -387,7 +387,7 @@
                              : MapConstant.DART_CLASS;
     ClassElement classElement = compiler.jsHelperLibrary.find(className);
     classElement.ensureResolved(compiler);
-    // TODO(floitsch): copy over the generic type.
+    // TODO(9476): copy over the generic type.
     DartType type = classElement.rawType;
     handler.registerInstantiatedClass(classElement, elements);
     Constant constant = new MapConstant(type, keysList, values, protoValue);
@@ -665,7 +665,7 @@
     List<Constant> jsNewArguments = evaluator.buildJsNewArguments(classElement);
 
     handler.registerInstantiatedClass(classElement, elements);
-    // TODO(floitsch): take generic types into account.
+    // TODO(9476): take generic types into account.
     classElement.computeType(compiler);
     DartType type = classElement.rawType;
     Constant constant = new ConstructedConstant(type, jsNewArguments);
diff --git a/sdk/lib/_internal/compiler/implementation/compiler.dart b/sdk/lib/_internal/compiler/implementation/compiler.dart
index 7a23913..4270b83 100644
--- a/sdk/lib/_internal/compiler/implementation/compiler.dart
+++ b/sdk/lib/_internal/compiler/implementation/compiler.dart
@@ -176,6 +176,12 @@
   ClassElement get typeImplementation => compiler.typeClass;
   ClassElement get boolImplementation => compiler.boolClass;
   ClassElement get nullImplementation => compiler.nullClass;
+
+  bool isDefaultNoSuchMethodImplementation(Element element) {
+    assert(element.name == Compiler.NO_SUCH_METHOD);
+    ClassElement classElement = element.getEnclosingClass();
+    return classElement == compiler.objectClass;
+  }
 }
 
 /**
diff --git a/sdk/lib/_internal/compiler/implementation/enqueue.dart b/sdk/lib/_internal/compiler/implementation/enqueue.dart
index 8c351c2..125a355 100644
--- a/sdk/lib/_internal/compiler/implementation/enqueue.dart
+++ b/sdk/lib/_internal/compiler/implementation/enqueue.dart
@@ -503,7 +503,8 @@
 
   void enableNoSuchMethod(Element element) {
     if (compiler.enabledNoSuchMethod) return;
-    if (element.getEnclosingClass() == compiler.objectClass) return;
+    if (compiler.backend.isDefaultNoSuchMethodImplementation(element)) return;
+
     Selector selector = new Selector.noSuchMethod();
     compiler.enabledNoSuchMethod = true;
     registerInvocation(Compiler.NO_SUCH_METHOD, selector);
diff --git a/sdk/lib/_internal/compiler/implementation/js_backend/backend.dart b/sdk/lib/_internal/compiler/implementation/js_backend/backend.dart
index b9b44ef..17ddd90 100644
--- a/sdk/lib/_internal/compiler/implementation/js_backend/backend.dart
+++ b/sdk/lib/_internal/compiler/implementation/js_backend/backend.dart
@@ -634,6 +634,7 @@
   final Map<Element, jsAst.Expression> generatedBailoutCode =
       new Map<Element, jsAst.Expression>();
 
+  ClassElement jsInterceptorClass;
   ClassElement jsStringClass;
   ClassElement jsArrayClass;
   ClassElement jsNumberClass;
@@ -838,7 +839,8 @@
     interceptedNames =
         compiler.findInterceptor(const SourceString('interceptedNames'));
     List<ClassElement> classes = [
-      compiler.objectClass,
+      jsInterceptorClass =
+          compiler.findInterceptor(const SourceString('Interceptor')),
       jsStringClass = compiler.findInterceptor(const SourceString('JSString')),
       jsArrayClass = compiler.findInterceptor(const SourceString('JSArray')),
       // The int class must be before the double class, because the
@@ -902,20 +904,30 @@
         compiler.objectClass, const SourceString('=='));
 
     specialOperatorEqClasses
-        ..add(jsNullClass)
-        ..add(jsNumberClass);
+        ..add(compiler.objectClass)
+        ..add(jsInterceptorClass)
+        ..add(jsNullClass);
+
+    validateInterceptorImplementsAllObjectMethods(jsInterceptorClass);
+  }
+
+  void validateInterceptorImplementsAllObjectMethods(
+      ClassElement interceptorClass) {
+    if (interceptorClass == null) return;
+    compiler.objectClass.forEachMember((_, Element member) {
+      if (member.isGenerativeConstructor()) return;
+      Element interceptorMember = interceptorClass.lookupMember(member.name);
+      // Interceptors must override all Object methods due to calling convention
+      // differences.
+      assert(interceptorMember.getEnclosingClass() != compiler.objectClass);
+    });
   }
 
   void addInterceptorsForNativeClassMembers(
       ClassElement cls, Enqueuer enqueuer) {
     if (enqueuer.isResolutionQueue) {
       cls.ensureResolved(compiler);
-      cls.forEachMember((ClassElement classElement, Element member) {
-          Set<Element> set = interceptedElements.putIfAbsent(
-              member.name, () => new Set<Element>());
-          set.add(member);
-        },
-        includeSuperMembers: true);
+      addInterceptorMembers(cls);
     }
   }
 
@@ -924,19 +936,25 @@
                        TreeElements elements) {
     if (enqueuer.isResolutionQueue) {
       cls.ensureResolved(compiler);
-      cls.forEachMember((ClassElement classElement, Element member) {
-          Set<Element> set = interceptedElements.putIfAbsent(
-              member.name, () => new Set<Element>());
-          set.add(member);
-        },
-        includeSuperMembers: true);
+      addInterceptorMembers(cls);
     }
     enqueuer.registerInstantiatedClass(cls, elements);
   }
 
+  void addInterceptorMembers(ClassElement cls) {
+    cls.forEachMember((ClassElement classElement, Element member) {
+        // All methods on [Object] are shadowed by [Interceptor].
+        if (classElement == compiler.objectClass) return;
+        Set<Element> set = interceptedElements.putIfAbsent(
+            member.name, () => new Set<Element>());
+        set.add(member);
+      },
+      includeSuperMembers: true);
+  }
+
   void registerSpecializedGetInterceptor(Set<ClassElement> classes) {
     String name = namer.getInterceptorName(getInterceptorMethod, classes);
-    if (classes.contains(compiler.objectClass)) {
+    if (classes.contains(jsInterceptorClass)) {
       // We can't use a specialized [getInterceptorMethod], so we make
       // sure we emit the one with all checks.
       specializedGetInterceptors[name] = interceptedClasses;
@@ -992,29 +1010,31 @@
       }
     }
     ClassElement result = null;
-    if (cls == compiler.stringClass) {
+    if (cls == compiler.stringClass || cls == jsStringClass) {
       addInterceptors(jsStringClass, enqueuer, elements);
-    } else if (cls == compiler.listClass) {
+    } else if (cls == compiler.listClass
+               || cls == jsArrayClass
+               || cls == jsFixedArrayClass
+               || cls == jsExtendableArrayClass) {
       addInterceptors(jsArrayClass, enqueuer, elements);
       enqueuer.registerInstantiatedClass(jsFixedArrayClass, elements);
       enqueuer.registerInstantiatedClass(jsExtendableArrayClass, elements);
-    } else if (cls == compiler.intClass) {
+    } else if (cls == compiler.intClass || cls == jsIntClass) {
       addInterceptors(jsIntClass, enqueuer, elements);
       addInterceptors(jsNumberClass, enqueuer, elements);
-    } else if (cls == compiler.doubleClass) {
+    } else if (cls == compiler.doubleClass || cls == jsDoubleClass) {
       addInterceptors(jsDoubleClass, enqueuer, elements);
       addInterceptors(jsNumberClass, enqueuer, elements);
-    } else if (cls == compiler.functionClass) {
+    } else if (cls == compiler.functionClass || cls == jsFunctionClass) {
       addInterceptors(jsFunctionClass, enqueuer, elements);
-    } else if (cls == compiler.boolClass) {
+    } else if (cls == compiler.boolClass || cls == jsBoolClass) {
       addInterceptors(jsBoolClass, enqueuer, elements);
-    } else if (cls == compiler.nullClass) {
+    } else if (cls == compiler.nullClass || cls == jsNullClass) {
       addInterceptors(jsNullClass, enqueuer, elements);
-    } else if (cls == compiler.numClass) {
+    } else if (cls == compiler.numClass || cls == jsNumberClass) {
       addInterceptors(jsIntClass, enqueuer, elements);
       addInterceptors(jsDoubleClass, enqueuer, elements);
       addInterceptors(jsNumberClass, enqueuer, elements);
-    } else if (cls == compiler.mapClass) {
     } else if (cls.isNative()) {
       addInterceptorsForNativeClassMembers(cls, enqueuer);
     }
@@ -1203,6 +1223,21 @@
     return rti.classesNeedingRti.contains(cls) || compiler.enabledRuntimeType;
   }
 
+  bool isDefaultNoSuchMethodImplementation(Element element) {
+    assert(element.name == Compiler.NO_SUCH_METHOD);
+    ClassElement classElement = element.getEnclosingClass();
+    return classElement == compiler.objectClass
+        || classElement == jsInterceptorClass;
+  }
+
+  bool isDefaultEqualityImplementation(Element element) {
+    assert(element.name == const SourceString('=='));
+    ClassElement classElement = element.getEnclosingClass();
+    return classElement == compiler.objectClass
+        || classElement == jsInterceptorClass
+        || classElement == jsNullClass;
+  }
+
   void enqueueInResolution(Element e, TreeElements elements) {
     if (e == null) return;
     ResolutionEnqueuer enqueuer = compiler.enqueuer.resolution;
diff --git a/sdk/lib/_internal/compiler/implementation/js_backend/namer.dart b/sdk/lib/_internal/compiler/implementation/js_backend/namer.dart
index 1d52f46..4a5623e 100644
--- a/sdk/lib/_internal/compiler/implementation/js_backend/namer.dart
+++ b/sdk/lib/_internal/compiler/implementation/js_backend/namer.dart
@@ -200,9 +200,11 @@
   final Map<Element, String> bailoutNames;
 
   final Map<Constant, String> constantNames;
+  ConstantCanonicalHasher constantHasher;
 
-  Namer(this.compiler)
-      : globals = new Map<Element, String>(),
+  Namer(Compiler compiler)
+      : compiler = compiler,
+        globals = new Map<Element, String>(),
         shortPrivateNameOwners = new Map<String, LibraryElement>(),
         bailoutNames = new Map<Element, String>(),
         usedGlobalNames = new Set<String>(),
@@ -213,7 +215,8 @@
         suggestedGlobalNames = new Map<String, String>(),
         suggestedInstanceNames = new Map<String, String>(),
         constantNames = new Map<Constant, String>(),
-        popularNameCounters = new Map<String, int>();
+        popularNameCounters = new Map<String, int>(),
+        constantHasher = new ConstantCanonicalHasher(compiler);
 
   String get isolateName => 'Isolate';
   String get isolatePropertiesName => r'$isolateProperties';
@@ -246,14 +249,8 @@
           longName = "C";
         }
       } else {
-        if (constant.isInterceptor()) {
-          InterceptorConstant interceptorConstant = constant;
-          String typeName =
-              interceptorConstant.dispatchedType.element.name.slowToString();
-          longName = typeName + '_methods';
-        } else {
-          longName = "CONSTANT";
-        }
+        longName = new ConstantNamingVisitor(compiler, constantHasher)
+            .getName(constant);
       }
       result = getFreshName(longName, usedGlobalNames, suggestedGlobalNames,
                             ensureSafe: true);
@@ -546,10 +543,12 @@
       if (cls == backend.jsStringClass) return "s";
       if (cls == backend.jsArrayClass) return "a";
       if (cls == backend.jsDoubleClass) return "d";
+      if (cls == backend.jsIntClass) return "i";
       if (cls == backend.jsNumberClass) return "n";
       if (cls == backend.jsNullClass) return "u";
       if (cls == backend.jsFunctionClass) return "f";
       if (cls == backend.jsBoolClass) return "b";
+      if (cls == backend.jsInterceptorClass) return "I";
       return cls.name.slowToString();
     }
     List<String> names = classes
@@ -567,9 +566,11 @@
   }
 
   String getInterceptorName(Element element, Collection<ClassElement> classes) {
-    if (classes.contains(compiler.objectClass)) {
-      // If the object class is in the set of intercepted classes, we
-      // need to go through the generic getInterceptorMethod.
+    JavaScriptBackend backend = compiler.backend;
+    if (classes.contains(backend.jsInterceptorClass)) {
+      // If the base Interceptor class is in the set of intercepted classes, we
+      // need to go through the generic getInterceptorMethod, since any subclass
+      // of the base Interceptor could match.
       return getName(element);
     }
     String suffix = getInterceptorSuffix(classes);
@@ -578,17 +579,19 @@
 
   String getOneShotInterceptorName(Selector selector,
                                    Collection<ClassElement> classes) {
+    JavaScriptBackend backend = compiler.backend;
     // The one-shot name is a global name derived from the invocation name.  To
     // avoid instability we would like the names to be unique and not clash with
     // other global names.
 
     String root = invocationName(selector);  // Is already safe.
 
-    if (classes.contains(compiler.objectClass)) {
-      // If the object class is in the set of intercepted classes, this is the
-      // most general specialization which uses the generic getInterceptor
-      // method.  To keep the name short, we add '$' only to distinguish from
-      // global getters or setters; operators and methods can't clash.
+    if (classes.contains(backend.jsInterceptorClass)) {
+      // If the base Interceptor class is in the set of intercepted classes,
+      // this is the most general specialization which uses the generic
+      // getInterceptor method.  To keep the name short, we add '$' only to
+      // distinguish from global getters or setters; operators and methods can't
+      // clash.
       // TODO(sra): Find a way to get the simple name when Object is not in the
       // set of classes for most general variant, e.g. "$lt$n" could be "$lt".
       if (selector.isGetter() || selector.isSetter()) root = '$root\$';
@@ -797,3 +800,324 @@
     }
   }
 }
+
+
+/**
+ * Generator of names for [Constant] values.
+ *
+ * The names are stable under perturbations of the source.  The name is either a
+ * short sequence of words, if this can be found from the constant, or a type
+ * followed by a hash tag.
+ *
+ *     List_imX                // A List, with hash tag.
+ *     C_Sentinel              // const Sentinel(),  "C_" added to avoid clash
+ *                             //   with class name.
+ *     JSInt_methods           // an interceptor.
+ *     Duration_16000          // const Duration(milliseconds: 16)
+ *     EventKeyProvider_keyup  // const EventKeyProvider('keyup')
+ *
+ */
+class ConstantNamingVisitor implements ConstantVisitor {
+
+  static final RegExp IDENTIFIER = new RegExp(r'^[A-Za-z_$][A-Za-z0-9_$]*$');
+  static const MAX_FRAGMENTS = 5;
+  static const MAX_EXTRA_LENGTH = 30;
+  static const DEFAULT_TAG_LENGTH = 3;
+
+  final Compiler compiler;
+  final ConstantCanonicalHasher hasher;
+
+  String root = null;     // First word, usually a type name.
+  bool failed = false;    // Failed to generate something pretty.
+  List<String> fragments = <String>[];
+  int length = 0;
+
+  ConstantNamingVisitor(this.compiler, this.hasher);
+
+  String getName(Constant constant) {
+    _visit(constant);
+    if (root == null) return 'CONSTANT';
+    if (failed) return '${root}_${getHashTag(constant, DEFAULT_TAG_LENGTH)}';
+    if (fragments.length == 1) return 'C_${root}';
+    return fragments.join('_');
+  }
+
+  String getHashTag(Constant constant, int width) =>
+      hashWord(hasher.getHash(constant), width);
+
+  String hashWord(int hash, int length) {
+    hash &= 0x1fffffff;
+    StringBuffer sb = new StringBuffer();
+    for (int i = 0; i < length; i++) {
+      int digit = hash % 62;
+      sb.write('0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ'
+          [digit]);
+      hash ~/= 62;
+      if (hash == 0) break;
+    }
+    return sb.toString();
+  }
+
+  void addRoot(String fragment) {
+    if (root == null && fragments.isEmpty) {
+      root = fragment;
+    }
+    add(fragment);
+  }
+
+  void add(String fragment) {
+    assert(fragment.length > 0);
+    fragments.add(fragment);
+    length += fragment.length;
+    if (fragments.length > MAX_FRAGMENTS) failed = true;
+    if (root != null && length > root.length + 1 + MAX_EXTRA_LENGTH) {
+      failed = true;
+    }
+  }
+
+  void addIdentifier(String fragment) {
+    if (fragment.length <= MAX_EXTRA_LENGTH && IDENTIFIER.hasMatch(fragment)) {
+      add(fragment);
+    } else {
+      failed = true;
+    }
+  }
+
+  _visit(Constant constant) {
+    return constant.accept(this);
+  }
+
+  visitSentinel(SentinelConstant constant) {
+    add(r'$');
+  }
+
+  visitFunction(FunctionConstant constant) {
+    add(constant.element.name.slowToString());
+  }
+
+  visitNull(NullConstant constant) {
+    add('null');
+  }
+
+  visitInt(IntConstant constant) {
+    // No `addRoot` since IntConstants are always inlined.
+    if (constant.value < 0) {
+      add('m${-constant.value}');
+    } else {
+      add('${constant.value}');
+    }
+  }
+
+  visitDouble(DoubleConstant constant) {
+    failed = true;
+  }
+
+  visitTrue(TrueConstant constant) {
+    add('true');
+  }
+
+  visitFalse(FalseConstant constant) {
+    add('false');
+  }
+
+  visitString(StringConstant constant) {
+    // No `addRoot` since string constants are always inlined.
+    addIdentifier(constant.value.slowToString());
+  }
+
+  visitList(ListConstant constant) {
+    // TODO(9476): Incorporate type parameters into name.
+    addRoot('List');
+    int length = constant.length;
+    if (constant.length == 0) {
+      add('empty');
+    } else if (length >= MAX_FRAGMENTS) {
+      failed = true;
+    } else {
+      for (int i = 0; i < length; i++) {
+        _visit(constant.entries[i]);
+        if (failed) break;
+      }
+    }
+  }
+
+  visitMap(MapConstant constant) {
+    // TODO(9476): Incorporate type parameters into name.
+    addRoot('Map');
+    if (constant.length == 0) {
+      add('empty');
+    } else {
+      // Using some bits from the keys hash tag groups the names Maps with the
+      // same structure.
+      add(getHashTag(constant.keys, 2) + getHashTag(constant, 3));
+    }
+  }
+
+  visitConstructed(ConstructedConstant constant) {
+    addRoot(constant.type.element.name.slowToString());
+    for (int i = 0; i < constant.fields.length; i++) {
+      _visit(constant.fields[i]);
+      if (failed) return;
+    }
+  }
+
+  visitType(TypeConstant constant) {
+    addRoot('Type');
+    DartType type = constant.representedType;
+    JavaScriptBackend backend = compiler.backend;
+    String name = backend.rti.getRawTypeRepresentation(type);
+    addIdentifier(name);
+  }
+
+  visitInterceptor(InterceptorConstant constant) {
+    addRoot(constant.dispatchedType.element.name.slowToString());
+    add('methods');
+  }
+}
+
+
+/**
+ * Generates canonical hash values for [Constant]s.
+ *
+ * Unfortunately, [Constant.hashCode] is not stable under minor perturbations,
+ * so it can't be used for generating names.  This hasher keeps consistency
+ * between runs by basing hash values of the names of elements, rather than
+ * their hashCodes.
+ */
+class ConstantCanonicalHasher implements ConstantVisitor<int> {
+
+  static const _MASK = 0x1fffffff;
+  static const _UINT32_LIMIT = 4 * 1024 * 1024 * 1024;
+
+
+  final Compiler compiler;
+  final Map<Constant, int> hashes = new Map<Constant, int>();
+
+  ConstantCanonicalHasher(this.compiler);
+
+  int getHash(Constant constant) => _visit(constant);
+
+  int _visit(Constant constant) {
+    int hash = hashes[constant];
+    if (hash == null) {
+      hash = _finish(constant.accept(this));
+      hashes[constant] = hash;
+    }
+    return hash;
+  }
+
+  int visitSentinel(SentinelConstant constant) => 1;
+  int visitNull(NullConstant constant) => 2;
+  int visitTrue(TrueConstant constant) => 3;
+  int visitFalse(FalseConstant constant) => 4;
+
+  int visitFunction(FunctionConstant constant) {
+    return _hashString(1, constant.element.name.slowToString());
+  }
+
+  int visitInt(IntConstant constant) => _hashInt(constant.value);
+
+  int visitDouble(DoubleConstant constant) => _hashDouble(constant.value);
+
+  int visitString(StringConstant constant) {
+    return _hashString(2, constant.value.slowToString());
+  }
+
+  int visitList(ListConstant constant) {
+    return _hashList(constant.length, constant.entries);
+  }
+
+  int visitMap(MapConstant constant) {
+    int hash = _visit(constant.keys);
+    return _hashList(hash, constant.values);
+  }
+
+  int visitConstructed(ConstructedConstant constant) {
+    int hash = _hashString(3, constant.type.element.name.slowToString());
+    for (int i = 0; i < constant.fields.length; i++) {
+      hash = _combine(hash, _visit(constant.fields[i]));
+    }
+    return hash;
+  }
+
+  int visitType(TypeConstant constant) {
+    DartType type = constant.representedType;
+    JavaScriptBackend backend = compiler.backend;
+    String name = backend.rti.getRawTypeRepresentation(type);
+    return _hashString(4, name);
+  }
+
+  visitInterceptor(InterceptorConstant constant) {
+    String typeName = constant.dispatchedType.element.name.slowToString();
+    return _hashString(5, typeName);
+  }
+
+  int _hashString(int hash, String s) {
+    int length = s.length;
+    hash = _combine(hash, length);
+    // Increasing stride is O(log N) on large strings which are unlikely to have
+    // many collisions.
+    for (int i = 0; i < length; i += 1 + (i >> 2)) {
+      hash = _combine(hash, s.codeUnitAt(i));
+    }
+    return hash;
+  }
+
+  int _hashList(int hash, List<Constant> constants) {
+    for (Constant constant in constants) {
+      hash = _combine(hash, _visit(constant));
+    }
+    return hash;
+  }
+
+  static int _hashInt(int value) {
+    if (value.abs() < _UINT32_LIMIT) return _MASK & value;
+    return _hashDouble(value.toDouble());
+  }
+
+  static int _hashDouble(double value) {
+    double magnitude = value.abs();
+    int sign = value < 0 ? 1 : 0;
+    if (magnitude < _UINT32_LIMIT) {  // 2^32
+      int intValue = value.toInt();
+      // Integer valued doubles in 32-bit range hash to the same values as ints.
+      int hash = _hashInt(intValue);
+      if (value == intValue) return hash;
+      hash = _combine(hash, sign);
+      int fraction = ((magnitude - intValue.abs()) * (_MASK + 1)).toInt();
+      hash = _combine(hash, fraction);
+      return hash;
+    } else if (value.isInfinite) {
+      return _combine(6, sign);
+    } else if (value.isNaN) {
+      return 7;
+    } else {
+      int hash = 0;
+      while (magnitude >= _UINT32_LIMIT) {
+        magnitude = magnitude / _UINT32_LIMIT;
+        hash++;
+      }
+      hash = _combine(hash, sign);
+      return _combine(hash, _hashDouble(magnitude));
+    }
+  }
+
+  /**
+   * [_combine] and [_finish] are parts of the [Jenkins hash function][1],
+   * modified by using masking to keep values in SMI range.
+   *
+   * [1]: http://en.wikipedia.org/wiki/Jenkins_hash_function
+   */
+  static int _combine(int hash, int value) {
+    hash = _MASK & (hash + value);
+    hash = _MASK & (hash + (((_MASK >> 10) & hash) << 10));
+    hash = hash ^ (hash >> 6);
+    return hash;
+  }
+
+  static int _finish(int hash) {
+    hash = _MASK & (hash + (((_MASK >> 3) & hash) <<  3));
+    hash = hash & (hash >> 11);
+    return _MASK & (hash + (((_MASK >> 15) & hash) << 15));
+  }
+}
diff --git a/sdk/lib/_internal/compiler/implementation/lib/interceptors.dart b/sdk/lib/_internal/compiler/implementation/lib/interceptors.dart
index f7c7cb8..42f19ba 100644
--- a/sdk/lib/_internal/compiler/implementation/lib/interceptors.dart
+++ b/sdk/lib/_internal/compiler/implementation/lib/interceptors.dart
@@ -48,12 +48,79 @@
 var interceptedNames;
 
 /**
+ * The base interceptor class.
+ *
+ * The code `r.foo(a)` is compiled to `getInterceptor(r).foo$1(r, a)`.  The
+ * value returned by [getInterceptor] holds the methods separately from the
+ * state of the instance.  The compiler converts the methods on an interceptor
+ * to take the Dart `this` argument as an explicit `receiver` argument.  The
+ * JavaScript `this` parameter is bound to the interceptor.
+ *
+ * In order to have uniform call sites, if a method is defined on an
+ * interceptor, methods of that name on plain unintercepted classes also use the
+ * interceptor calling convention.  The plain classes are _self-interceptors_,
+ * and for them, `getInterceptor(r)` returns `r`.  Methods on plain
+ * unintercepted classes have a redundant `receiver` argument and should ignore
+ * it in favour of `this`.
+ *
+ * In the case of mixins, a method may be placed on both an intercepted class
+ * and an unintercepted class.  In this case, the method must use the `receiver`
+ * parameter.
+ *
+ *
+ * There are various optimizations of the general call pattern.
+ *
+ * When the interceptor can be statically determined, it can be used directly:
+ *
+ *     CONSTANT_INTERCEPTOR.foo$1(r, a)
+ *
+ * If there are only a few classes, [getInterceptor] can be specialized with a
+ * more efficient dispatch:
+ *
+ *     getInterceptor$specialized(r).foo$1(r, a)
+ *
+ * If it can be determined that the receiver is an unintercepted class, it can
+ * be called directly:
+ *
+ *     r.foo$1(r, a)
+ *
+ * If, further, it is known that the call site cannot call a foo that is
+ * mixed-in to a native class, then it is known that the explicit receiver is
+ * ignored, and space-saving dummy value can be passed instead:
+ *
+ *     r.foo$1(0, a)
+ *
+ * This class defines implementations of *all* methods on [Object] so no
+ * interceptor inherits an implementation from [Object].  This enables the
+ * implementations on Object to ignore the explicit receiver argument, which
+ * allows dummy receiver optimization.
+ */
+abstract class Interceptor {
+  const Interceptor();
+
+  bool operator ==(other) => identical(this, other);
+
+  int get hashCode => Primitives.objectHashCode(this);
+
+  String toString() => Primitives.objectToString(this);
+
+  dynamic noSuchMethod(InvocationMirror invocation) {
+    throw new NoSuchMethodError(this,
+                                invocation.memberName,
+                                invocation.positionalArguments,
+                                invocation.namedArguments);
+  }
+
+  Type get runtimeType;
+}
+
+/**
  * The interceptor class for tear-off static methods. Unlike
  * tear-off instance methods, tear-off static methods are just the JS
  * function, and methods inherited from Object must therefore be
  * intercepted.
  */
-class JSFunction implements Function {
+class JSFunction extends Interceptor implements Function {
   const JSFunction();
   String toString() => 'Closure';
 }
@@ -61,7 +128,7 @@
 /**
  * The interceptor class for [bool].
  */
-class JSBool implements bool {
+class JSBool extends Interceptor implements bool {
   const JSBool();
 
   // Note: if you change this, also change the function [S].
@@ -81,7 +148,7 @@
  * the methods on Object assume the receiver is non-null.  This means that
  * JSNull will always be in the interceptor set for methods defined on Object.
  */
-class JSNull implements Null {
+class JSNull extends Interceptor implements Null {
   const JSNull();
 
   bool operator ==(other) => identical(null, other);
diff --git a/sdk/lib/_internal/compiler/implementation/lib/js_array.dart b/sdk/lib/_internal/compiler/implementation/lib/js_array.dart
index c86a14f..ef4aecd 100644
--- a/sdk/lib/_internal/compiler/implementation/lib/js_array.dart
+++ b/sdk/lib/_internal/compiler/implementation/lib/js_array.dart
@@ -10,7 +10,7 @@
  * actually use the receiver of the method, which is generated as an extra
  * argument added to each member.
  */
-class JSArray<E> implements List<E>, JSIndexable {
+class JSArray<E> extends Interceptor implements List<E>, JSIndexable {
   const JSArray();
 
   void add(E value) {
diff --git a/sdk/lib/_internal/compiler/implementation/lib/js_helper.dart b/sdk/lib/_internal/compiler/implementation/lib/js_helper.dart
index 155a74a..a3a59aa 100644
--- a/sdk/lib/_internal/compiler/implementation/lib/js_helper.dart
+++ b/sdk/lib/_internal/compiler/implementation/lib/js_helper.dart
@@ -43,10 +43,18 @@
 
 String S(value) {
   if (value is String) return value;
-  if ((value is num && value != 0) || value is bool) {
-    return JS('String', r'String(#)', value);
+  if (value is num) {
+    if (value != 0) {
+      // ""+x is faster than String(x) for integers on most browsers.
+      return JS('String', r'"" + (#)', value);
+    }
+  } else if (true == value) {
+    return 'true';
+  } else if (false == value) {
+    return 'false';
+  } else if (value == null) {
+    return 'null';
   }
-  if (value == null) return 'null';
   var res = value.toString();
   if (res is !String) throw new ArgumentError(value);
   return res;
diff --git a/sdk/lib/_internal/compiler/implementation/lib/js_number.dart b/sdk/lib/_internal/compiler/implementation/lib/js_number.dart
index c6b78bc8..e95d651 100644
--- a/sdk/lib/_internal/compiler/implementation/lib/js_number.dart
+++ b/sdk/lib/_internal/compiler/implementation/lib/js_number.dart
@@ -13,7 +13,7 @@
  * Note that none of the methods here delegate to a method defined on JSInt or
  * JSDouble.  This is exploited in [tryComputeConstantInterceptor].
  */
-class JSNumber implements num {
+class JSNumber extends Interceptor implements num {
   const JSNumber();
 
   int compareTo(num b) {
@@ -146,7 +146,7 @@
     if (this == 0 && JS('bool', '(1 / #) < 0', this)) {
       return '-0.0';
     } else {
-      return JS('String', r'String(#)', this);
+      return JS('String', r'"" + (#)', this);
     }
   }
 
diff --git a/sdk/lib/_internal/compiler/implementation/lib/js_string.dart b/sdk/lib/_internal/compiler/implementation/lib/js_string.dart
index 1b8fef0..57e2c45 100644
--- a/sdk/lib/_internal/compiler/implementation/lib/js_string.dart
+++ b/sdk/lib/_internal/compiler/implementation/lib/js_string.dart
@@ -10,7 +10,7 @@
  * actually use the receiver of the method, which is generated as an extra
  * argument added to each member.
  */
-class JSString implements String, JSIndexable {
+class JSString extends Interceptor implements String, JSIndexable {
   const JSString();
 
   int codeUnitAt(int index) {
diff --git a/sdk/lib/_internal/compiler/implementation/lib/scalarlist_patch.dart b/sdk/lib/_internal/compiler/implementation/lib/scalarlist_patch.dart
index 4106c98..326b892 100644
--- a/sdk/lib/_internal/compiler/implementation/lib/scalarlist_patch.dart
+++ b/sdk/lib/_internal/compiler/implementation/lib/scalarlist_patch.dart
@@ -128,33 +128,3 @@
     throw new UnsupportedError('Float64List.view');
   }
 }
-
-patch class Float32x4 {
-  patch factory Float32x4(double x, double y, double z, double w) {
-    throw new UnsupportedError('Float32x4');
-  }
-  patch factory Float32x4.zero() {
-    throw new UnsupportedError('Float32x4.zero');
-  }
-}
-
-patch class Uint32x4 {
-  patch factory Uint32x4(int x, int y, int z, int w) {
-    throw new UnsupportedError('Uint32x4');
-  }
-  patch factory Uint32x4.bool(bool x, bool y, bool z, bool w) {
-    throw new UnsupportedError('Uint32x4.bool');
-  }
-}
-
-
-patch class Float32x4List {
-  patch factory Float32x4List(int length) {
-    throw new UnsupportedError('Float32x4List');
-  }
-
-  patch factory Float32x4List.view(ByteArray array,
-                                   [int start = 0, int length]) {
-    throw new UnsupportedError('Float32x4List.view');
-  }
-}
diff --git a/sdk/lib/_internal/compiler/implementation/lib/typeddata_patch.dart b/sdk/lib/_internal/compiler/implementation/lib/typeddata_patch.dart
index 8dd7bcc..28d2233 100644
--- a/sdk/lib/_internal/compiler/implementation/lib/typeddata_patch.dart
+++ b/sdk/lib/_internal/compiler/implementation/lib/typeddata_patch.dart
@@ -139,6 +139,38 @@
 }
 
 
+patch class Float32x4List {
+  patch factory Float32x4List(int length) {
+    throw new UnsupportedError('Float32x4List');
+  }
+
+  patch factory Float32x4List.view(ByteBuffer buffer,
+                                      [int offsetInBytes = 0, int length]) {
+    throw new UnsupportedError('Float32x4List.view');
+  }
+}
+
+
+patch class Float32x4 {
+  patch factory Float32x4(double x, double y, double z, double w) {
+    throw new UnsupportedError('Float32x4');
+  }
+  patch factory Float32x4.zero() {
+    throw new UnsupportedError('Float32x4.zero');
+  }
+}
+
+
+patch class Uint32x4 {
+  patch factory Uint32x4(int x, int y, int z, int w) {
+    throw new UnsupportedError('Uint32x4');
+  }
+  patch factory Uint32x4.bool(bool x, bool y, bool z, bool w) {
+    throw new UnsupportedError('Uint32x4.bool');
+  }
+}
+
+
 patch class ByteData {
   patch factory ByteData(int length) {
     throw new UnsupportedError('ByteData');
diff --git a/sdk/lib/_internal/compiler/implementation/ssa/builder.dart b/sdk/lib/_internal/compiler/implementation/ssa/builder.dart
index 37e3b14..affa364 100644
--- a/sdk/lib/_internal/compiler/implementation/ssa/builder.dart
+++ b/sdk/lib/_internal/compiler/implementation/ssa/builder.dart
@@ -296,7 +296,7 @@
     JavaScriptBackend backend = compiler.backend;
     if (backend.isInterceptedMethod(element)) {
       bool isInterceptorClass = backend.isInterceptorClass(cls.declaration);
-      SourceString name = (cls == compiler.objectClass || isInterceptorClass)
+      SourceString name = isInterceptorClass
           ? const SourceString('receiver')
           : const SourceString('_');
       Element parameter = new InterceptedElement(
@@ -886,27 +886,10 @@
     assert(elements[function] != null);
     openFunction(functionElement, function);
     SourceString name = functionElement.name;
-    // If [functionElement] is operator== we explicitely add a null
-    // check at the beginning of the method. This is to avoid having
-    // call sites do the null check.
+    // If [functionElement] is `operator==` we explicitely add a null check at
+    // the beginning of the method. This is to avoid having call sites do the
+    // null check.
     if (name == const SourceString('==')) {
-      if (functionElement.getEnclosingClass() == compiler.objectClass) {
-        // We special case [Object.operator==] because we know the receiver is
-        // not null (that case goes via a call site check or the JSNull
-        // interceptor) and therefore can just do an identity check on `this`.
-
-        // TODO(sra): This method uses the explicit receiver calling convention
-        // so that interceptors may inherit it.  If we make all interceptors
-        // inherit from a common Interceptor class, we can switch back to the
-        // 'ignored receiver' convention.
-        HInstruction parameter = parameters.values.first;
-        HIdentity identity =
-            new HIdentity(graph.explicitReceiverParameter, parameter);
-        add(identity);
-        HReturn ret = new HReturn(identity);
-        close(ret).addSuccessor(graph.exit);
-        return closeFunction();
-      }
       if (!backend.operatorEqHandlesNullArgument(functionElement)) {
         handleIf(
             function,
@@ -2457,7 +2440,10 @@
     stack.add(value);
   }
 
-  void generateSetter(SendSet send, Element element, HInstruction value) {
+  void generateNonInstanceSetter(SendSet send,
+                                 Element element,
+                                 HInstruction value) {
+    assert(!Elements.isInstanceSend(send, elements));
     if (Elements.isStaticOrTopLevelField(element)) {
       if (element.isSetter()) {
         HStatic target = new HStatic(element);
@@ -2470,9 +2456,6 @@
         addWithPosition(new HStaticStore(element, value), send);
       }
       stack.add(value);
-    } else if (element == null || Elements.isInstanceField(element)) {
-      HInstruction receiver = generateInstanceSendReceiver(send);
-      generateInstanceSetterWithCompiledReceiver(send, receiver, value);
     } else if (Elements.isErroneousElement(element)) {
       // An erroneous element indicates an unresolved static setter.
       generateThrowNoSuchMethod(send,
@@ -3732,9 +3715,14 @@
     } else if (const SourceString("=") == op.source) {
       Link<Node> link = node.arguments;
       assert(!link.isEmpty && link.tail.isEmpty);
-      visit(link.head);
-      HInstruction value = pop();
-      generateSetter(node, element, value);
+      if (Elements.isInstanceSend(node, elements)) {
+        HInstruction receiver = generateInstanceSendReceiver(node);
+        visit(link.head);
+        generateInstanceSetterWithCompiledReceiver(node, receiver, pop());
+      } else {
+        visit(link.head);
+        generateNonInstanceSetter(node, element, pop());
+      }
     } else if (identical(op.source.stringValue, "is")) {
       compiler.internalError("is-operator as SendSet", node: op);
     } else {
@@ -3760,7 +3748,7 @@
         generateInstanceSetterWithCompiledReceiver(node, receiver, value);
       } else {
         assert(receiver == null);
-        generateSetter(node, element, value);
+        generateNonInstanceSetter(node, element, value);
       }
       if (node.isPostfix) {
         pop();
@@ -4760,6 +4748,10 @@
   void visitExpression(Node node) {
     node.accept(builder);
     HInstruction expression = builder.pop();
+    if (!expression.isConstantString()) {
+      expression = new HStringify(expression, node);
+      builder.add(expression);
+    }
     result = (result == null) ? expression : concat(result, expression);
   }
 
diff --git a/sdk/lib/_internal/compiler/implementation/ssa/codegen.dart b/sdk/lib/_internal/compiler/implementation/ssa/codegen.dart
index b8843da..af3528c 100644
--- a/sdk/lib/_internal/compiler/implementation/ssa/codegen.dart
+++ b/sdk/lib/_internal/compiler/implementation/ssa/codegen.dart
@@ -1586,7 +1586,7 @@
         backend.compiler.enabledInvokeOn) {
       return selector;
     }
-    HType receiverType = node.dartReceiver.instructionType;
+    HType receiverType = node.getDartReceiver(compiler).instructionType;
     return receiverType.refine(selector, compiler);
   }
 
@@ -2074,34 +2074,34 @@
   }
 
   void visitStringConcat(HStringConcat node) {
-    if (isEmptyString(node.left)) {
-      useStringified(node.right);
-   } else if (isEmptyString(node.right)) {
-      useStringified(node.left);
-    } else {
-      useStringified(node.left);
-      js.Expression left = pop();
-      useStringified(node.right);
-      push(new js.Binary("+", left, pop()), node);
-    }
+    use(node.left);
+    js.Expression jsLeft = pop();
+    use(node.right);
+    push(new js.Binary('+', jsLeft, pop()), node);
   }
 
-  bool isEmptyString(HInstruction node) {
-    if (!node.isConstantString()) return false;
-    HConstant constant = node;
-    StringConstant string = constant.constant;
-    return string.value.length == 0;
-  }
-
-  void useStringified(HInstruction node) {
-    if (node.isString()) {
-      use(node);
+  void visitStringify(HStringify node) {
+    HInstruction input = node.inputs.first;
+    if (input.isString()) {
+      use(input);
+    } else if (input.isInteger() || input.isBoolean()) {
+      // JavaScript's + operator with a string for the left operand will convert
+      // the right operand to a string, and the conversion result is correct.
+      use(input);
+      if (node.usedBy.length == 1
+          && node.usedBy[0] is HStringConcat
+          && node.usedBy[0].inputs[1] == node) {
+        // The context is already <string> + value.
+      } else {
+        // Force an empty string for the first operand.
+        push(new js.Binary('+', js.string(""), pop()), node);
+      }
     } else {
       Element convertToString = backend.getStringInterpolationHelper();
       world.registerStaticUse(convertToString);
       js.VariableUse variableUse =
           new js.VariableUse(backend.namer.isolateAccess(convertToString));
-      use(node);
+      use(input);
       push(new js.Call(variableUse, <js.Expression>[pop()]), node);
     }
   }
diff --git a/sdk/lib/_internal/compiler/implementation/ssa/invoke_dynamic_specializers.dart b/sdk/lib/_internal/compiler/implementation/ssa/invoke_dynamic_specializers.dart
index 1cfc99d..6895f44 100644
--- a/sdk/lib/_internal/compiler/implementation/ssa/invoke_dynamic_specializers.dart
+++ b/sdk/lib/_internal/compiler/implementation/ssa/invoke_dynamic_specializers.dart
@@ -544,13 +544,15 @@
     if (right.isConstantNull() || instructionType.isPrimitiveOrNull()) {
       return newBuiltinVariant(left, right);
     }
-    // Make the mask non-nullable to avoid finding a potential
-    // JSNull::operator==.
-    TypeMask mask = instructionType.computeMask(compiler).nonNullable();
+    TypeMask mask = instructionType.computeMask(compiler);
     Selector selector = new TypedSelector(mask, instruction.selector);
     World world = compiler.world;
     JavaScriptBackend backend = compiler.backend;
-    if (world.locateSingleElement(selector) == backend.objectEquals) {
+    Iterable<Element> matches = world.allFunctions.filter(selector);
+    // This test relies the on `Object.==` and `Interceptor.==` always being
+    // implemented because if the selector matches by subtype, it still will be
+    // a regular object or an interceptor.
+    if (matches.every(backend.isDefaultEqualityImplementation)) {
       return newBuiltinVariant(left, right);
     }
     return null;
diff --git a/sdk/lib/_internal/compiler/implementation/ssa/nodes.dart b/sdk/lib/_internal/compiler/implementation/ssa/nodes.dart
index 84de9d5..e6cfe3c 100644
--- a/sdk/lib/_internal/compiler/implementation/ssa/nodes.dart
+++ b/sdk/lib/_internal/compiler/implementation/ssa/nodes.dart
@@ -59,6 +59,7 @@
   R visitStatic(HStatic node);
   R visitStaticStore(HStaticStore node);
   R visitStringConcat(HStringConcat node);
+  R visitStringify(HStringify node);
   R visitSubtract(HSubtract node);
   R visitSwitch(HSwitch node);
   R visitThis(HThis node);
@@ -335,6 +336,7 @@
   visitStatic(HStatic node) => visitInstruction(node);
   visitStaticStore(HStaticStore node) => visitInstruction(node);
   visitStringConcat(HStringConcat node) => visitInstruction(node);
+  visitStringify(HStringify node) => visitInstruction(node);
   visitThis(HThis node) => visitParameterValue(node);
   visitThrow(HThrow node) => visitControlFlow(node);
   visitTry(HTry node) => visitControlFlow(node);
@@ -1083,7 +1085,7 @@
   bool isConstantTrue() => false;
   bool isConstantSentinel() => false;
 
-  bool isInterceptor() => false;
+  bool isInterceptor(Compiler compiler) => false;
 
   bool isValid() {
     HValidator validator = new HValidator();
@@ -1316,7 +1318,9 @@
           : const InvokeDynamicSpecializer();
   toString() => 'invoke dynamic: $selector';
   HInstruction get receiver => inputs[0];
-  HInstruction get dartReceiver => isCallOnInterceptor ? inputs[1] : inputs[0];
+  HInstruction getDartReceiver(Compiler compiler) {
+    return isCallOnInterceptor(compiler) ? inputs[1] : inputs[0];
+  }
 
   /**
    * Returns whether this call is on an intercepted method.
@@ -1331,8 +1335,8 @@
   /**
    * Returns whether this call is on an interceptor object.
    */
-  bool get isCallOnInterceptor {
-    return isInterceptedCall && receiver.isInterceptor();
+  bool isCallOnInterceptor(Compiler compiler) {
+    return isInterceptedCall && receiver.isInterceptor(compiler);
   }
 
   int typeCode() => HInstruction.INVOKE_DYNAMIC_TYPECODE;
@@ -1457,6 +1461,17 @@
     }
   }
 
+  bool isInterceptor(Compiler compiler) {
+    if (sourceElement == null) return false;
+    // In case of a closure inside an interceptor class, [:this:] is
+    // stored in the generated closure class, and accessed through a
+    // [HFieldGet].
+    JavaScriptBackend backend = compiler.backend;
+    bool interceptor =
+        backend.isInterceptorClass(sourceElement.getEnclosingClass());
+    return interceptor && sourceElement is ThisElement;
+  }
+
   bool canThrow() => receiver.canBeNull();
 
   accept(HVisitor visitor) => visitor.visitFieldGet(this);
@@ -1842,7 +1857,7 @@
   bool isConstantTrue() => constant.isTrue();
   bool isConstantSentinel() => constant.isSentinel();
 
-  bool isInterceptor() => constant.isInterceptor();
+  bool isInterceptor(Compiler compiler) => constant.isInterceptor();
 
   // Maybe avoid this if the literal is big?
   bool isCodeMotionInvariant() => true;
@@ -1888,6 +1903,10 @@
   toString() => 'this';
   accept(HVisitor visitor) => visitor.visitThis(this);
   bool isCodeMotionInvariant() => true;
+  bool isInterceptor(Compiler compiler) {
+    JavaScriptBackend backend = compiler.backend;
+    return backend.isInterceptorClass(sourceElement.getEnclosingClass());
+  }
 }
 
 class HPhi extends HInstruction {
@@ -2034,7 +2053,7 @@
   String toString() => 'interceptor on $interceptedClasses';
   accept(HVisitor visitor) => visitor.visitInterceptor(this);
   HInstruction get receiver => inputs[0];
-  bool isInterceptor() => true;
+  bool isInterceptor(Compiler compiler) => true;
 
   int typeCode() => HInstruction.INTERCEPTOR_TYPECODE;
   bool typeEquals(other) => other is HInterceptor;
@@ -2063,7 +2082,7 @@
     assert(inputs[0] is HConstant);
     assert(inputs[0].instructionType == HType.NULL);
   }
-  bool get isCallOnInterceptor => true;
+  bool isCallOnInterceptor(Compiler compiler) => true;
 
   String toString() => 'one shot interceptor on $selector';
   accept(HVisitor visitor) => visitor.visitOneShotInterceptor(this);
@@ -2256,7 +2275,9 @@
   final Node node;
   HStringConcat(HInstruction left, HInstruction right, this.node)
       : super(<HInstruction>[left, right]) {
-    setAllSideEffects();
+    // TODO(sra): Until Issue 9293 is fixed, this false dependency keeps the
+    // concats bunched with stringified inputs for much better looking code with
+    // fewer temps.
     setDependsOnSomething();
     instructionType = HType.STRING;
   }
@@ -2268,6 +2289,22 @@
   toString() => "string concat";
 }
 
+/**
+ * The part of string interpolation which converts and interpolated expression
+ * into a String value.
+ */
+class HStringify extends HInstruction {
+  final Node node;
+  HStringify(HInstruction input, this.node) : super(<HInstruction>[input]) {
+    setAllSideEffects();
+    setDependsOnSomething();
+    instructionType = HType.STRING;
+  }
+
+  accept(HVisitor visitor) => visitor.visitStringify(this);
+  toString() => "stringify";
+}
+
 /** Non-block-based (aka. traditional) loop information. */
 class HLoopInformation {
   final HBasicBlock header;
diff --git a/sdk/lib/_internal/compiler/implementation/ssa/optimize.dart b/sdk/lib/_internal/compiler/implementation/ssa/optimize.dart
index 2a189f2..ec9c47d 100644
--- a/sdk/lib/_internal/compiler/implementation/ssa/optimize.dart
+++ b/sdk/lib/_internal/compiler/implementation/ssa/optimize.dart
@@ -329,7 +329,7 @@
       if (folded != node) return folded;
     }
 
-    HType receiverType = node.dartReceiver.instructionType;
+    HType receiverType = node.getDartReceiver(compiler).instructionType;
     Selector selector = receiverType.refine(node.selector, compiler);
     Element element = compiler.world.locateSingleElement(selector);
     // TODO(ngeoffray): Also fold if it's a getter or variable.
@@ -594,10 +594,10 @@
       HInstruction folded = handleInterceptedCall(node);
       if (folded != node) return folded;
     }
-    Element field = findConcreteFieldForDynamicAccess(
-        node.dartReceiver, node.selector);
+    HInstruction receiver = node.getDartReceiver(compiler);
+    Element field = findConcreteFieldForDynamicAccess(receiver, node.selector);
     if (field == null) return node;
-    return directFieldGet(node.dartReceiver, field);
+    return directFieldGet(receiver, field);
   }
 
   HInstruction directFieldGet(HInstruction receiver, Element field) {
@@ -643,8 +643,8 @@
       if (folded != node) return folded;
     }
 
-    Element field = findConcreteFieldForDynamicAccess(
-        node.dartReceiver, node.selector);
+    HInstruction receiver = node.getDartReceiver(compiler);
+    Element field = findConcreteFieldForDynamicAccess(receiver, node.selector);
     if (field == null || !field.isAssignable()) return node;
     // Use [:node.inputs.last:] in case the call follows the
     // interceptor calling convention, but is not a call on an
@@ -660,20 +660,60 @@
         value = other;
       }
     }
-    return new HFieldSet(field, node.inputs[0], value);
+    return new HFieldSet(field, receiver, value);
   }
 
   HInstruction visitStringConcat(HStringConcat node) {
-    DartString folded = const LiteralDartString("");
-    for (int i = 0; i < node.inputs.length; i++) {
-      HInstruction part = node.inputs[i];
-      if (!part.isConstant()) return node;
-      HConstant constant = part;
+    // Simplify string concat:
+    //
+    //     "" + R                ->  R
+    //     L + ""                ->  L
+    //     "L" + "R"             ->  "LR"
+    //     (prefix + "L") + "R"  ->  prefix + "LR"
+    //
+    StringConstant getString(HInstruction instruction) {
+      if (!instruction.isConstantString()) return null;
+      HConstant constant = instruction;
+      return constant.constant;
+    }
+
+    StringConstant leftString = getString(node.left);
+    if (leftString != null && leftString.value.length == 0) return node.right;
+
+    StringConstant rightString = getString(node.right);
+    if (rightString == null) return node;
+    if (rightString.value.length == 0) return node.left;
+
+    HInstruction prefix = null;
+    if (leftString == null) {
+      if (node.left is! HStringConcat) return node;
+      HStringConcat leftConcat = node.left;
+      // Don't undo CSE.
+      if (leftConcat.usedBy.length != 1) return node;
+      prefix = leftConcat.left;
+      leftString = getString(leftConcat.right);
+      if (leftString == null) return node;
+    }
+
+    HInstruction folded =
+        graph.addConstant(constantSystem.createString(
+            new DartString.concat(leftString.value, rightString.value),
+            node.node));
+    if (prefix == null) return folded;
+    return new HStringConcat(prefix, folded, node.node);
+  }
+
+  HInstruction visitStringify(HStringify node) {
+    HInstruction input = node.inputs[0];
+    if (input.isString()) return input;
+    if (input.isConstant()) {
+      HConstant constant = input;
       if (!constant.constant.isPrimitive()) return node;
       PrimitiveConstant primitive = constant.constant;
-      folded = new DartString.concat(folded, primitive.toDartString());
+      return graph.addConstant(constantSystem.createString(
+          primitive.toDartString(), node.node));
     }
-    return graph.addConstant(constantSystem.createString(folded, node.node));
+    return node;
   }
 
   HInstruction visitInterceptor(HInterceptor node) {
diff --git a/sdk/lib/_internal/compiler/implementation/ssa/tracer.dart b/sdk/lib/_internal/compiler/implementation/ssa/tracer.dart
index bb1044b..57545f9 100644
--- a/sdk/lib/_internal/compiler/implementation/ssa/tracer.dart
+++ b/sdk/lib/_internal/compiler/implementation/ssa/tracer.dart
@@ -455,6 +455,10 @@
     return "StringConcat: $leftId + $rightId";
   }
 
+  String visitStringify(HStringify node) {
+    return "Stringify: ${node.inputs[0]}";
+  }
+
   String visitSubtract(HSubtract node) => handleInvokeBinary(node, '-');
 
   String visitSwitch(HSwitch node) {
diff --git a/sdk/lib/_internal/compiler/implementation/ssa/types_propagation.dart b/sdk/lib/_internal/compiler/implementation/ssa/types_propagation.dart
index 2d6b6f2..b5accc2 100644
--- a/sdk/lib/_internal/compiler/implementation/ssa/types_propagation.dart
+++ b/sdk/lib/_internal/compiler/implementation/ssa/types_propagation.dart
@@ -126,7 +126,7 @@
   }
 
   HType visitInvokeDynamic(HInvokeDynamic instruction) {
-    HType receiverType = instruction.dartReceiver.instructionType;
+    HType receiverType = instruction.getDartReceiver(compiler).instructionType;
     Selector refined = receiverType.refine(instruction.selector, compiler);
     HType type = new HType.inferredTypeForSelector(refined, compiler);
     if (type.isUseful()) return type;
diff --git a/sdk/lib/_internal/dartdoc/bin/dartdoc.dart b/sdk/lib/_internal/dartdoc/bin/dartdoc.dart
index 3c906bf..c84c72c 100644
--- a/sdk/lib/_internal/dartdoc/bin/dartdoc.dart
+++ b/sdk/lib/_internal/dartdoc/bin/dartdoc.dart
@@ -19,11 +19,10 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../lib/dartdoc.dart';
-
 // TODO(rnystrom): Use "package:" URL (#4968).
-import '../../../../../pkg/args/lib/args.dart';
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import '../lib/dartdoc.dart';
+import 'package:args/args.dart';
+import 'package:pathos/path.dart' as path;
 
 /**
  * Run this from the `lib/_internal/dartdoc` directory.
diff --git a/sdk/lib/_internal/dartdoc/lib/universe_serializer.dart b/sdk/lib/_internal/dartdoc/lib/universe_serializer.dart
index b88c9ea..edeca41 100755
--- a/sdk/lib/_internal/dartdoc/lib/universe_serializer.dart
+++ b/sdk/lib/_internal/dartdoc/lib/universe_serializer.dart
@@ -11,7 +11,7 @@
 import 'dartdoc.dart';
 
 // TODO(rnystrom): Use "package:" URL (#4968).
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 import '../../compiler/implementation/mirrors/dart2js_mirror.dart' as dart2js;
 import '../../compiler/implementation/mirrors/mirrors.dart';
 import '../../compiler/implementation/mirrors/mirrors_util.dart';
diff --git a/sdk/lib/_internal/dartdoc/pubspec.yaml b/sdk/lib/_internal/dartdoc/pubspec.yaml
index abeff7b..b28d984 100644
--- a/sdk/lib/_internal/dartdoc/pubspec.yaml
+++ b/sdk/lib/_internal/dartdoc/pubspec.yaml
@@ -1,3 +1,10 @@
 name: dartdoc
 description: >
  Libraries for generating documentation from Dart source code.
+
+dependencies:
+  args: ">=0.4.2 <1.0.0"
+  pathos: ">=0.4.2 <1.0.0"
+
+dev_dependencies:
+  unittest: ">=0.4.2 <1.0.0"
diff --git a/sdk/lib/_internal/dartdoc/test/dartdoc_test.dart b/sdk/lib/_internal/dartdoc/test/dartdoc_test.dart
index e588aa5..e5b6787 100644
--- a/sdk/lib/_internal/dartdoc/test/dartdoc_test.dart
+++ b/sdk/lib/_internal/dartdoc/test/dartdoc_test.dart
@@ -7,16 +7,15 @@
 
 import 'dart:async';
 import 'dart:io';
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+
+import 'package:pathos/path.dart' as path;
+import 'package:unittest/unittest.dart';
 
 // TODO(rnystrom): Use "package:" URL (#4968).
 import '../lib/dartdoc.dart' as dd;
 import '../lib/markdown.dart';
 import 'markdown_test.dart';
 
-// TODO(rnystrom): Better path to unittest.
-import '../../../../../pkg/unittest/lib/unittest.dart';
-
 // Pretty test config with --human
 import '../../../../../utils/tests/pub/command_line_config.dart';
 
@@ -237,11 +236,8 @@
   expect(_runDartdoc(libraryPaths).then(eval), completes);
 }
 
-/// Runs dartdoc with the libraryPaths provided, and completes to dartdoc's
-/// ProcessResult.
-Future<ProcessResult> _runDartdoc(List<String> libraryPaths) {
-  var dartBin = new Options().executable;
-
+/// The path to the root directory of the dartdoc entrypoint.
+String get _dartdocDir {
   var dir = path.absolute(new Options().script);
   while (path.basename(dir) != 'dartdoc') {
     if (!path.absolute(dir).contains('dartdoc') || dir == path.dirname(dir)) {
@@ -249,9 +245,40 @@
     }
     dir = path.dirname(dir);
   }
-  var dartdoc = path.join(path.absolute(dir), 'bin/dartdoc.dart');
+  return path.absolute(dir);
+}
 
-  final runArgs = [dartdoc];
+/// The path to use for the package root for subprocesses.
+String get _packageRoot {
+  var sdkVersionPath = path.join(_dartdocDir, '..', '..', '..', 'version');
+  if (new File(sdkVersionPath).existsSync()) {
+    // It looks like dartdoc is being run from the SDK, so we should set the
+    // package root to the SDK's packages directory.
+    return path.absolute(path.join(_dartdocDir, '..', '..', '..', 'packages'));
+  }
+
+  // It looks like Dartdoc is being run from the Dart repo, so the package root
+  // is in the build output directory. We can find that directory relative to
+  // the Dart executable, but that could be in one of two places: in
+  // "$BUILD/dart" or "$BUILD/dart-sdk/bin/dart".
+  var executableDir = path.dirname(new Options().executable);
+  if (new Directory(path.join(executableDir, 'dart-sdk')).existsSync()) {
+    // The executable is in "$BUILD/dart".
+    return path.absolute(path.join(executableDir, 'packages'));
+  } else {
+    // The executable is in "$BUILD/dart-sdk/bin/dart".
+    return path.absolute(path.join(executableDir, '..', '..', 'packages'));
+  }
+}
+
+/// Runs dartdoc with the libraryPaths provided, and completes to dartdoc's
+/// ProcessResult.
+Future<ProcessResult> _runDartdoc(List<String> libraryPaths) {
+  var dartBin = new Options().executable;
+
+  var dartdoc = path.join(_dartdocDir, 'bin/dartdoc.dart');
+
+  final runArgs = ['--package-root=$_packageRoot/', dartdoc];
 
   // Turn relative libraryPaths to absolute ones.
   runArgs.addAll(libraryPaths
diff --git a/sdk/lib/_internal/dartdoc/test/markdown_test.dart b/sdk/lib/_internal/dartdoc/test/markdown_test.dart
index 44c9431..aff43da 100644
--- a/sdk/lib/_internal/dartdoc/test/markdown_test.dart
+++ b/sdk/lib/_internal/dartdoc/test/markdown_test.dart
@@ -5,12 +5,11 @@
 /// Unit tests for markdown.
 library markdownTests;
 
+import 'package:unittest/unittest.dart';
+
 // TODO(rnystrom): Use "package:" URL (#4968).
 import '../lib/markdown.dart';
 
-// TODO(rnystrom): Better path to unittest.
-import '../../../../../pkg/unittest/lib/unittest.dart';
-
 /// Most of these tests are based on observing how showdown behaves:
 /// http://softwaremaniacs.org/playground/showdown-highlight/
 void main() {
diff --git a/sdk/lib/chrome/dart2js/chrome_dart2js.dart b/sdk/lib/chrome/dart2js/chrome_dart2js.dart
index 7c1ca62..2c416c4 100644
--- a/sdk/lib/chrome/dart2js/chrome_dart2js.dart
+++ b/sdk/lib/chrome/dart2js/chrome_dart2js.dart
@@ -59,7 +59,7 @@
   /*
    * JS Object Representation
    */
-  Object _jsObject;
+  final Object _jsObject;
 }
 
 /**
@@ -196,12 +196,12 @@
   /*
    * JS Object Representation
    */
-  Object _jsObject;
+  final Object _jsObject;
 
   /*
    * Number of arguments the callback takes.
    */
-  int _callbackArity;
+  final int _callbackArity;
 
   /*
    * Private constructor
@@ -329,7 +329,7 @@
   /*
    * JS Variable
    */
-  Object _jsObject;
+  final Object _jsObject;
 
   /*
    * Members
diff --git a/sdk/lib/crypto/crypto.dart b/sdk/lib/crypto/crypto.dart
index 755c18b..f22e2ab 100644
--- a/sdk/lib/crypto/crypto.dart
+++ b/sdk/lib/crypto/crypto.dart
@@ -6,10 +6,148 @@
 
 import 'dart:math';
 
-part 'crypto_base.dart';
 part 'crypto_utils.dart';
 part 'hash_utils.dart';
 part 'hmac.dart';
 part 'md5.dart';
 part 'sha1.dart';
 part 'sha256.dart';
+
+/**
+ * Interface for cryptographic hash functions.
+ *
+ * The [add] method is used to add data to the hash. The [close] method
+ * is used to extract the message digest.
+ *
+ * Once the [close] method has been called no more data can be added using the
+ * [add] method. If [add] is called after the first call to [close] a
+ * HashException is thrown.
+ *
+ * If multiple instances of a given Hash is needed the [newInstance]
+ * method can provide a new instance.
+ */
+// TODO(floitsch): make Hash implement Sink, EventSink or similar.
+abstract class Hash {
+  /**
+   * Add a list of bytes to the hash computation.
+   */
+  add(List<int> data);
+
+  /**
+   * Finish the hash computation and extract the message digest as
+   * a list of bytes.
+   */
+  List<int> close();
+
+  /**
+   * Returns a new instance of this hash function.
+   */
+  Hash newInstance();
+
+  /**
+   * Internal block size of the hash in bytes.
+   *
+   * This is exposed for use by the HMAC class which needs to know the
+   * block size for the [Hash] it is using.
+   */
+  int get blockSize;
+}
+
+/**
+ * SHA1 hash function implementation.
+ */
+abstract class SHA1 implements Hash {
+  factory SHA1() => new _SHA1();
+}
+
+/**
+ * SHA256 hash function implementation.
+ */
+abstract class SHA256 implements Hash {
+  factory SHA256() => new _SHA256();
+}
+
+/**
+ * MD5 hash function implementation.
+ *
+ * WARNING: MD5 has known collisions and should only be used when
+ * required for backwards compatibility.
+ */
+abstract class MD5 implements Hash {
+  factory MD5() => new _MD5();
+}
+
+/**
+ * Hash-based Message Authentication Code support.
+ *
+ * The [add] method is used to add data to the message. The [digest] and
+ * [close] methods are used to extract the message authentication code.
+ */
+// TODO(floitsch): make Hash implement Sink, EventSink or similar.
+abstract class HMAC {
+  /**
+   * Create an [HMAC] object from a [Hash] and a key.
+   */
+  factory HMAC(Hash hash, List<int> key) => new _HMAC(hash, key);
+
+  /**
+   * Add a list of bytes to the message.
+   */
+  add(List<int> data);
+
+  /**
+   * Perform the actual computation and extract the message digest
+   * as a list of bytes.
+   */
+  List<int> close();
+
+  /**
+   * Extract the message digest as a list of bytes without closing [this].
+   */
+  List<int> get digest;
+
+  /**
+   * Verify that the HMAC computed for the data so far matches the
+   * given message digest.
+   *
+   * This method should be used instead of memcmp-style comparisons
+   * to avoid leaking information via timing.
+   *
+   * Throws an exception if the given digest does not have the same
+   * size as the digest computed by this HMAC instance.
+   */
+  bool verify(List<int> digest);
+}
+
+/**
+ * Utility methods for working with message digests.
+ */
+abstract class CryptoUtils {
+  /**
+   * Convert a list of bytes (for example a message digest) into a hex
+   * string.
+   */
+  static String bytesToHex(List<int> bytes) {
+    return _CryptoUtils.bytesToHex(bytes);
+  }
+
+  /**
+   * Converts a list of bytes (for example a message digest) into a
+   * base64 encoded string optionally broken up in to lines of
+   * [lineLength] chars separated by '\r\n'.
+   */
+  static String bytesToBase64(List<int> bytes, [int lineLength]) {
+    return _CryptoUtils.bytesToBase64(bytes, lineLength);
+  }
+}
+
+/**
+ * HashExceptions are thrown on invalid use of a Hash
+ * object.
+ */
+class HashException {
+  HashException(String this.message);
+  toString() => "HashException: $message";
+  String message;
+}
+
diff --git a/sdk/lib/crypto/crypto_base.dart b/sdk/lib/crypto/crypto_base.dart
deleted file mode 100644
index d1666b5..0000000
--- a/sdk/lib/crypto/crypto_base.dart
+++ /dev/null
@@ -1,144 +0,0 @@
-// Copyright (c) 2013, 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 dart.crypto;
-
-/**
- * Interface for cryptographic hash functions.
- *
- * The [add] method is used to add data to the hash. The [close] method
- * is used to extract the message digest.
- *
- * Once the [close] method has been called no more data can be added using the
- * [add] method. If [add] is called after the first call to [close] a
- * HashException is thrown.
- *
- * If multiple instances of a given Hash is needed the [newInstance]
- * method can provide a new instance.
- */
-// TODO(floitsch): make Hash implement Sink, EventSink or similar.
-abstract class Hash {
-  /**
-   * Add a list of bytes to the hash computation.
-   */
-  add(List<int> data);
-
-  /**
-   * Finish the hash computation and extract the message digest as
-   * a list of bytes.
-   */
-  List<int> close();
-
-  /**
-   * Returns a new instance of this hash function.
-   */
-  Hash newInstance();
-
-  /**
-   * Internal block size of the hash in bytes.
-   *
-   * This is exposed for use by the HMAC class which needs to know the
-   * block size for the [Hash] it is using.
-   */
-  int get blockSize;
-}
-
-/**
- * SHA1 hash function implementation.
- */
-abstract class SHA1 implements Hash {
-  factory SHA1() => new _SHA1();
-}
-
-/**
- * SHA256 hash function implementation.
- */
-abstract class SHA256 implements Hash {
-  factory SHA256() => new _SHA256();
-}
-
-/**
- * MD5 hash function implementation.
- *
- * WARNING: MD5 has known collisions and should only be used when
- * required for backwards compatibility.
- */
-abstract class MD5 implements Hash {
-  factory MD5() => new _MD5();
-}
-
-/**
- * Hash-based Message Authentication Code support.
- *
- * The [add] method is used to add data to the message. The [digest] and
- * [close] methods are used to extract the message authentication code.
- */
-// TODO(floitsch): make Hash implement Sink, EventSink or similar.
-abstract class HMAC {
-  /**
-   * Create an [HMAC] object from a [Hash] and a key.
-   */
-  factory HMAC(Hash hash, List<int> key) => new _HMAC(hash, key);
-
-  /**
-   * Add a list of bytes to the message.
-   */
-  add(List<int> data);
-
-  /**
-   * Perform the actual computation and extract the message digest
-   * as a list of bytes.
-   */
-  List<int> close();
-
-  /**
-   * Extract the message digest as a list of bytes without closing [this].
-   */
-  List<int> get digest;
-
-  /**
-   * Verify that the HMAC computed for the data so far matches the
-   * given message digest.
-   *
-   * This method should be used instead of memcmp-style comparisons
-   * to avoid leaking information via timing.
-   *
-   * Throws an exception if the given digest does not have the same
-   * size as the digest computed by this HMAC instance.
-   */
-  bool verify(List<int> digest);
-}
-
-/**
- * Utility methods for working with message digests.
- */
-abstract class CryptoUtils {
-  /**
-   * Convert a list of bytes (for example a message digest) into a hex
-   * string.
-   */
-  static String bytesToHex(List<int> bytes) {
-    return _CryptoUtils.bytesToHex(bytes);
-  }
-
-  /**
-   * Converts a list of bytes (for example a message digest) into a
-   * base64 encoded string optionally broken up in to lines of
-   * [lineLength] chars separated by '\r\n'.
-   */
-  static String bytesToBase64(List<int> bytes, [int lineLength]) {
-    return _CryptoUtils.bytesToBase64(bytes, lineLength);
-  }
-}
-
-/**
- * HashExceptions are thrown on invalid use of a Hash
- * object.
- */
-class HashException {
-  HashException(String this.message);
-  toString() => "HashException: $message";
-  String message;
-}
-
diff --git a/sdk/lib/crypto/crypto_sources.gypi b/sdk/lib/crypto/crypto_sources.gypi
index de6faf9..8d9fbd8 100644
--- a/sdk/lib/crypto/crypto_sources.gypi
+++ b/sdk/lib/crypto/crypto_sources.gypi
@@ -7,7 +7,6 @@
   'sources': [
     'crypto.dart',
     # The above file needs to be first as it lists the parts below.
-    'crypto_base.dart',
     'crypto_utils.dart',
     'hash_utils.dart',
     'hmac.dart',
diff --git a/sdk/lib/html/dart2js/html_dart2js.dart b/sdk/lib/html/dart2js/html_dart2js.dart
index 53b3e08..018b8aa 100644
--- a/sdk/lib/html/dart2js/html_dart2js.dart
+++ b/sdk/lib/html/dart2js/html_dart2js.dart
@@ -9516,6 +9516,14 @@
   @DocsEditable
   final String tagName;
 
+  @JSName('webkitInsertionParent')
+  @DomName('Element.webkitInsertionParent')
+  @DocsEditable
+  @SupportedBrowser(SupportedBrowser.CHROME)
+  @SupportedBrowser(SupportedBrowser.SAFARI)
+  @Experimental
+  final Node insertionParent;
+
   @JSName('webkitPseudo')
   @DomName('Element.webkitPseudo')
   @DocsEditable
@@ -16535,6 +16543,10 @@
   @DocsEditable
   void endOfStream(String error) native;
 
+  @DomName('MediaSource.isTypeSupported')
+  @DocsEditable
+  static bool isTypeSupported(String type) native;
+
   @JSName('removeEventListener')
   @DomName('MediaSource.removeEventListener')
   @DocsEditable
@@ -19892,18 +19904,10 @@
   @DocsEditable
   static const EventStreamProvider<RtcDataChannelEvent> dataChannelEvent = const EventStreamProvider<RtcDataChannelEvent>('datachannel');
 
-  @DomName('RTCPeerConnection.gatheringchangeEvent')
-  @DocsEditable
-  static const EventStreamProvider<Event> gatheringChangeEvent = const EventStreamProvider<Event>('gatheringchange');
-
   @DomName('RTCPeerConnection.icecandidateEvent')
   @DocsEditable
   static const EventStreamProvider<RtcIceCandidateEvent> iceCandidateEvent = const EventStreamProvider<RtcIceCandidateEvent>('icecandidate');
 
-  @DomName('RTCPeerConnection.icechangeEvent')
-  @DocsEditable
-  static const EventStreamProvider<Event> iceChangeEvent = const EventStreamProvider<Event>('icechange');
-
   @DomName('RTCPeerConnection.negotiationneededEvent')
   @DocsEditable
   static const EventStreamProvider<Event> negotiationNeededEvent = const EventStreamProvider<Event>('negotiationneeded');
@@ -19912,10 +19916,6 @@
   @DocsEditable
   static const EventStreamProvider<MediaStreamEvent> removeStreamEvent = const EventStreamProvider<MediaStreamEvent>('removestream');
 
-  @DomName('RTCPeerConnection.statechangeEvent')
-  @DocsEditable
-  static const EventStreamProvider<Event> stateChangeEvent = const EventStreamProvider<Event>('statechange');
-
   @DomName('RTCPeerConnection.iceConnectionState')
   @DocsEditable
   final String iceConnectionState;
@@ -19928,10 +19928,6 @@
   @DocsEditable
   final RtcSessionDescription localDescription;
 
-  @DomName('RTCPeerConnection.readyState')
-  @DocsEditable
-  final String readyState;
-
   @DomName('RTCPeerConnection.remoteDescription')
   @DocsEditable
   final RtcSessionDescription remoteDescription;
@@ -20135,18 +20131,10 @@
   @DocsEditable
   Stream<RtcDataChannelEvent> get onDataChannel => dataChannelEvent.forTarget(this);
 
-  @DomName('RTCPeerConnection.ongatheringchange')
-  @DocsEditable
-  Stream<Event> get onGatheringChange => gatheringChangeEvent.forTarget(this);
-
   @DomName('RTCPeerConnection.onicecandidate')
   @DocsEditable
   Stream<RtcIceCandidateEvent> get onIceCandidate => iceCandidateEvent.forTarget(this);
 
-  @DomName('RTCPeerConnection.onicechange')
-  @DocsEditable
-  Stream<Event> get onIceChange => iceChangeEvent.forTarget(this);
-
   @DomName('RTCPeerConnection.onnegotiationneeded')
   @DocsEditable
   Stream<Event> get onNegotiationNeeded => negotiationNeededEvent.forTarget(this);
@@ -20155,10 +20143,6 @@
   @DocsEditable
   Stream<MediaStreamEvent> get onRemoveStream => removeStreamEvent.forTarget(this);
 
-  @DomName('RTCPeerConnection.onstatechange')
-  @DocsEditable
-  Stream<Event> get onStateChange => stateChangeEvent.forTarget(this);
-
 }
 
 
@@ -20212,6 +20196,10 @@
   @DocsEditable
   final dynamic _get_timestamp;
 
+  @DomName('RTCStatsReport.type')
+  @DocsEditable
+  final String type;
+
   @DomName('RTCStatsReport.names')
   @DocsEditable
   List<String> names() native;
@@ -21412,15 +21400,9 @@
 @Experimental
 class SpeechRecognitionEvent extends Event native "*SpeechRecognitionEvent" {
 
-  @DomName('SpeechRecognitionEvent.result')
+  @DomName('SpeechRecognitionEvent.emma')
   @DocsEditable
-  final SpeechRecognitionResult result;
-
-  @DomName('SpeechRecognitionEvent.resultHistory')
-  @DocsEditable
-  @Returns('_SpeechRecognitionResultList')
-  @Creates('_SpeechRecognitionResultList')
-  final List<SpeechRecognitionResult> resultHistory;
+  final Document emma;
 
   @DomName('SpeechRecognitionEvent.resultIndex')
   @DocsEditable
@@ -22058,6 +22040,14 @@
 class Text extends CharacterData native "*Text" {
   factory Text(String data) => _TextFactoryProvider.createText(data);
 
+  @JSName('webkitInsertionParent')
+  @DomName('Text.webkitInsertionParent')
+  @DocsEditable
+  @SupportedBrowser(SupportedBrowser.CHROME)
+  @SupportedBrowser(SupportedBrowser.SAFARI)
+  @Experimental
+  final Node insertionParent;
+
   @DomName('Text.wholeText')
   @DocsEditable
   final String wholeText;
@@ -24691,6 +24681,23 @@
 
 
 @DocsEditable
+@DomName('WebGLCompressedTexturePVRTC')
+class WebGLCompressedTexturePvrtc native "*WebGLCompressedTexturePVRTC" {
+
+  static const int COMPRESSED_RGBA_PVRTC_2BPPV1_IMG = 0x8C03;
+
+  static const int COMPRESSED_RGBA_PVRTC_4BPPV1_IMG = 0x8C02;
+
+  static const int COMPRESSED_RGB_PVRTC_2BPPV1_IMG = 0x8C01;
+
+  static const int COMPRESSED_RGB_PVRTC_4BPPV1_IMG = 0x8C00;
+}
+// Copyright (c) 2012, 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.
+
+
+@DocsEditable
 @DomName('WebGLCompressedTextureS3TC')
 class WebGLCompressedTextureS3TC native "*WebGLCompressedTextureS3TC" {
 
@@ -27739,6 +27746,14 @@
   int setTimeout(Object handler, int timeout) native;
 
   @JSName('webkitRequestFileSystem')
+  /**
+   * Access a sandboxed file system of the specified `size`. If `persistent` is
+   * true, the application will request permission from the user to create
+   * lasting storage. This storage cannot be freed without the user's
+   * permission. Returns a [Future] whose value stores a reference to the
+   * sandboxed file system for use. Because the file system is sandboxed,
+   * applications cannot access file systems created in other web pages. 
+   */
   @DomName('WorkerContext.webkitRequestFileSystem')
   @DocsEditable
   @SupportedBrowser(SupportedBrowser.CHROME)
@@ -27746,6 +27761,14 @@
   void __requestFileSystem(int type, int size, [_FileSystemCallback successCallback, _ErrorCallback errorCallback]) native;
 
   @JSName('webkitRequestFileSystem')
+  /**
+   * Access a sandboxed file system of the specified `size`. If `persistent` is
+   * true, the application will request permission from the user to create
+   * lasting storage. This storage cannot be freed without the user's
+   * permission. Returns a [Future] whose value stores a reference to the
+   * sandboxed file system for use. Because the file system is sandboxed,
+   * applications cannot access file systems created in other web pages. 
+   */
   @DomName('WorkerContext.webkitRequestFileSystem')
   @DocsEditable
   @SupportedBrowser(SupportedBrowser.CHROME)
@@ -27759,6 +27782,14 @@
   }
 
   @JSName('webkitRequestFileSystemSync')
+  /**
+   * Access a sandboxed file system of the specified `size`. If `persistent` is
+   * true, the application will request permission from the user to create
+   * lasting storage. This storage cannot be freed without the user's
+   * permission. This call will block until a reference to the synchronous file 
+   * system API has been obtained. Because the file system is sandboxed,
+   * applications cannot access file systems created in other web pages. 
+   */
   @DomName('WorkerContext.webkitRequestFileSystemSync')
   @DocsEditable
   @SupportedBrowser(SupportedBrowser.CHROME)
@@ -27870,6 +27901,22 @@
   @DomName('WorkerNavigator.userAgent')
   @DocsEditable
   final String userAgent;
+
+  @JSName('webkitPersistentStorage')
+  @DomName('WorkerNavigator.webkitPersistentStorage')
+  @DocsEditable
+  @SupportedBrowser(SupportedBrowser.CHROME)
+  @SupportedBrowser(SupportedBrowser.SAFARI)
+  @Experimental
+  final StorageQuota persistentStorage;
+
+  @JSName('webkitTemporaryStorage')
+  @DomName('WorkerNavigator.webkitTemporaryStorage')
+  @DocsEditable
+  @SupportedBrowser(SupportedBrowser.CHROME)
+  @SupportedBrowser(SupportedBrowser.SAFARI)
+  @Experimental
+  final StorageQuota temporaryStorage;
 }
 // Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file
 // for details. All rights reserved. Use of this source code is governed by a
@@ -31219,17 +31266,10 @@
 
 
 /**
- * Works with KeyboardEvent and KeyEvent to determine how to expose information
- * about Key(board)Events. This class functions like an EventListenerList, and
- * provides a consistent interface for the Dart
- * user, despite the fact that a multitude of browsers that have varying
- * keyboard default behavior.
- *
- * This class is very much a work in progress, and we'd love to get information
- * on how we can make this class work with as many international keyboards as
- * possible. Bugs welcome!
+ * Internal class that does the actual calculations to determine keyCode and
+ * charCode for keydown, keypress, and keyup events for all browsers.
  */
-class KeyboardEventController {
+class _KeyboardEventHandler extends EventStreamProvider<KeyEvent> {
   // This code inspired by Closure's KeyHandling library.
   // http://closure-library.googlecode.com/svn/docs/closure_goog_events_keyhandler.js.source.html
 
@@ -31237,29 +31277,28 @@
    * The set of keys that have been pressed down without seeing their
    * corresponding keyup event.
    */
-  List<KeyboardEvent> _keyDownList;
-
-  /** The set of functions that wish to be notified when a KeyEvent happens. */
-  List<Function> _callbacks;
+  final List<KeyboardEvent> _keyDownList = <KeyboardEvent>[];
 
   /** The type of KeyEvent we are tracking (keyup, keydown, keypress). */
-  String _type;
+  final String _type;
 
   /** The element we are watching for events to happen on. */
-  EventTarget _target;
+  final EventTarget _target;
 
   // The distance to shift from upper case alphabet Roman letters to lower case.
-  final int _ROMAN_ALPHABET_OFFSET = "a".codeUnits[0] - "A".codeUnits[0];
+  static final int _ROMAN_ALPHABET_OFFSET = "a".codeUnits[0] - "A".codeUnits[0];
 
-  StreamSubscription _keyUpSubscription, _keyDownSubscription,
-      _keyPressSubscription;
+  /** Controller to produce KeyEvents for the stream. */
+  final StreamController _controller = new StreamController.broadcast();
+
+  static const _EVENT_TYPE = 'KeyEvent';
 
   /**
    * An enumeration of key identifiers currently part of the W3C draft for DOM3
    * and their mappings to keyCodes.
    * http://www.w3.org/TR/DOM-Level-3-Events/keyset.html#KeySet-Set
    */
-  static Map<String, int> _keyIdentifier = {
+  static const Map<String, int> _keyIdentifier = const {
     'Up': KeyCode.UP,
     'Down': KeyCode.DOWN,
     'Left': KeyCode.LEFT,
@@ -31285,53 +31324,48 @@
     'Insert': KeyCode.INSERT
   };
 
-  /** Named constructor to add an onKeyPress event listener to our handler. */
-  KeyboardEventController.keypress(EventTarget target) {
-    _KeyboardEventController(target, 'keypress');
+  /** Return a stream for KeyEvents for the specified target. */
+  Stream<KeyEvent> forTarget(EventTarget e, {bool useCapture: false}) {
+    return new _KeyboardEventHandler.initializeAllEventListeners(
+        _type, e).stream;
   }
 
-  /** Named constructor to add an onKeyUp event listener to our handler. */
-  KeyboardEventController.keyup(EventTarget target) {
-    _KeyboardEventController(target, 'keyup');
-  }
-
-  /** Named constructor to add an onKeyDown event listener to our handler. */
-  KeyboardEventController.keydown(EventTarget target) {
-    _KeyboardEventController(target, 'keydown');
+  /**
+   * Accessor to the stream associated with a particular KeyboardEvent
+   * EventTarget.
+   *
+   * [forTarget] must be called to initialize this stream to listen to a
+   * particular EventTarget.
+   */
+  Stream<KeyEvent> get stream {
+    if(_target != null) {
+      return _controller.stream;
+    } else {
+      throw new StateError("Not initialized. Call forTarget to access a stream "
+          "initialized with a particular EventTarget.");
+    }
   }
 
   /**
    * General constructor, performs basic initialization for our improved
    * KeyboardEvent controller.
    */
-  _KeyboardEventController(EventTarget target, String type) {
-    _callbacks = [];
-    _type = type;
-    _target = target;
+  _KeyboardEventHandler(this._type) :
+    _target = null, super(_EVENT_TYPE) {
   }
 
   /**
    * Hook up all event listeners under the covers so we can estimate keycodes
    * and charcodes when they are not provided.
    */
-  void _initializeAllEventListeners() {
-    _keyDownList = [];
-    if (_keyDownSubscription == null) {
-      _keyDownSubscription = Element.keyDownEvent.forTarget(
-          _target, useCapture: true).listen(processKeyDown);
-      _keyPressSubscription = Element.keyPressEvent.forTarget(
-          _target, useCapture: true).listen(processKeyUp);
-      _keyUpSubscription = Element.keyUpEvent.forTarget(
-          _target, useCapture: true).listen(processKeyPress);
-    }
-  }
-
-  /** Add a callback that wishes to be notified when a KeyEvent occurs. */
-  void add(void callback(KeyEvent)) {
-    if (_callbacks.length == 0) {
-      _initializeAllEventListeners();
-    }
-    _callbacks.add(callback);
+  _KeyboardEventHandler.initializeAllEventListeners(this._type, this._target) : 
+    super(_EVENT_TYPE) {
+    Element.keyDownEvent.forTarget(_target, useCapture: true).listen(
+        processKeyDown);
+    Element.keyPressEvent.forTarget(_target, useCapture: true).listen(
+        processKeyPress);
+    Element.keyUpEvent.forTarget(_target, useCapture: true).listen(
+        processKeyUp);
   }
 
   /**
@@ -31339,31 +31373,8 @@
    * occurred.
    */
   bool _dispatch(KeyEvent event) {
-    if (event.type == _type) {
-      // Make a copy of the listeners in case a callback gets removed while
-      // dispatching from the list.
-      List callbacksCopy = new List.from(_callbacks);
-      for(var callback in callbacksCopy) {
-        callback(event);
-      }
-    }
-  }
-
-  /** Remove the given callback from the listeners list. */
-  void remove(void callback(KeyEvent)) {
-    var index = _callbacks.indexOf(callback);
-    if (index != -1) {
-      _callbacks.removeAt(index);
-    }
-    if (_callbacks.length == 0) {
-      // If we have no listeners, don't bother keeping track of keypresses.
-      _keyDownSubscription.cancel();
-      _keyDownSubscription = null;
-      _keyPressSubscription.cancel();
-      _keyPressSubscription = null;
-      _keyUpSubscription.cancel();
-      _keyUpSubscription = null;
-    }
+    if (event.type == _type)
+      _controller.add(event);
   }
 
   /** Determine if caps lock is one of the currently depressed keys. */
@@ -31551,7 +31562,7 @@
          _keyDownList.last.keyCode == KeyCode.ALT && !e.altKey ||
          Device.userAgent.contains('Mac') &&
          _keyDownList.last.keyCode == KeyCode.META && !e.metaKey)) {
-      _keyDownList = [];
+      _keyDownList.clear();
     }
 
     var event = new KeyEvent(e);
@@ -31611,8 +31622,7 @@
       }
     }
     if (toRemove != null) {
-      _keyDownList =
-          _keyDownList.where((element) => element != toRemove).toList();
+      _keyDownList.removeWhere((element) => element == toRemove);
     } else if (_keyDownList.length > 0) {
       // This happens when we've reached some international keyboard case we
       // haven't accounted for or we haven't correctly eliminated all browser
@@ -31622,6 +31632,37 @@
     _dispatch(e);
   }
 }
+
+
+/**
+ * Records KeyboardEvents that occur on a particular element, and provides a
+ * stream of outgoing KeyEvents with cross-browser consistent keyCode and
+ * charCode values despite the fact that a multitude of browsers that have
+ * varying keyboard default behavior.
+ *
+ * Example usage:
+ *
+ *     KeyboardEventStream.onKeyDown(document.body).listen(
+ *         keydownHandlerTest);
+ *
+ * This class is very much a work in progress, and we'd love to get information
+ * on how we can make this class work with as many international keyboards as
+ * possible. Bugs welcome!
+ */
+class KeyboardEventStream {
+
+  /** Named constructor to produce a stream for onKeyPress events. */
+  static Stream<KeyEvent> onKeyPress(EventTarget target) =>
+      new _KeyboardEventHandler('keypress').forTarget(target);
+
+  /** Named constructor to produce a stream for onKeyUp events. */
+  static Stream<KeyEvent> onKeyUp(EventTarget target) =>
+      new _KeyboardEventHandler('keyup').forTarget(target);
+
+  /** Named constructor to produce a stream for onKeyDown events. */
+  static Stream<KeyEvent> onKeyDown(EventTarget target) =>
+    new _KeyboardEventHandler('keydown').forTarget(target);
+}
 // Copyright (c) 2012, 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.
@@ -32739,6 +32780,39 @@
   timer = new _Timer(() { canceller(id); });
   return timer;
 };
+
+class _PureIsolateTimer implements Timer {
+  final ReceivePort _port = new ReceivePort();
+  SendPort _sendPort; // Effectively final.
+
+  _PureIsolateTimer(int milliSeconds, callback, repeating) {
+    _sendPort = _port.toSendPort();
+    _port.receive((msg, replyTo) {
+      assert(msg == _TIMER_PING);
+      assert(replyTo == _HELPER_ISOLATE_PORT);
+      callback(this);
+      if (!repeating) _cancel();
+    });
+    _HELPER_ISOLATE_PORT.then((port) {
+      port.send([_NEW_TIMER, milliSeconds, repeating], _sendPort);
+    });
+  }
+
+  void cancel() {
+    _cancel();
+    _HELPER_ISOLATE_PORT.then((port) {
+      port.send([_CANCEL_TIMER], _sendPort);
+    });
+  }
+
+  void _cancel() {
+    _port.close();
+  }
+}
+
+get _pureIsolateTimerFactoryClosure =>
+    ((int milliSeconds, void callback(Timer time), bool repeating) =>
+        new _PureIsolateTimer(milliSeconds, callback, repeating));
 // Copyright (c) 2012, 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.
@@ -32830,7 +32904,7 @@
 // The receiver is JS.
 class _JsSendPortSync implements SendPortSync {
 
-  num _id;
+  final num _id;
   _JsSendPortSync(this._id);
 
   callSync(var message) {
@@ -33000,7 +33074,7 @@
  */
 abstract class _MicrotaskScheduler {
   bool _nextMicrotaskFrameScheduled = false;
-  _MicrotaskCallback _callback;
+  final _MicrotaskCallback _callback;
 
   _MicrotaskScheduler(this._callback);
 
@@ -33614,7 +33688,7 @@
   // Private window.  Note, this is a window in another frame, so it
   // cannot be typed as "Window" as its prototype is not patched
   // properly.  Its fields and methods can only be accessed via JavaScript.
-  var _window;
+  final _window;
 
   // Fields.
   HistoryBase get history =>
@@ -33709,6 +33783,9 @@
  * inconsistencies, and also provide both keyCode and charCode information
  * for all key events (when such information can be determined).
  *
+ * KeyEvent tries to provide a higher level, more polished keyboard event
+ * information on top of the "raw" [KeyboardEvent].
+ *
  * This class is very much a work in progress, and we'd love to get information
  * on how we can make this class work with as many international keyboards as
  * possible. Bugs welcome!
@@ -33747,7 +33824,7 @@
   /** Accessor to the underlying altKey value is the parent event. */
   bool get _realAltKey => JS('int', '#.altKey', _parent);
 
-  /** Construct a KeyEvent with [parent] as event we're emulating. */
+  /** Construct a KeyEvent with [parent] as the event we're emulating. */
   KeyEvent(KeyboardEvent parent) {
     _parent = parent;
     _shadowAltKey = _realAltKey;
@@ -33755,6 +33832,18 @@
     _shadowKeyCode = _realKeyCode;
   }
 
+  // TODO(efortuna): If KeyEvent is sufficiently successful that we want to make
+  // it the default keyboard event handling, move these methods over to Element.
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyDownEvent =
+    new _KeyboardEventHandler('keydown');
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyUpEvent =
+    new _KeyboardEventHandler('keyup');
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyPressEvent =
+    new _KeyboardEventHandler('keypress');
+
   /** True if the altGraphKey is pressed during this event. */
   bool get altGraphKey => _parent.altGraphKey;
   bool get bubbles => _parent.bubbles;
diff --git a/sdk/lib/html/dartium/html_dartium.dart b/sdk/lib/html/dartium/html_dartium.dart
index e1424ad..d7bb433 100644
--- a/sdk/lib/html/dartium/html_dartium.dart
+++ b/sdk/lib/html/dartium/html_dartium.dart
@@ -10082,6 +10082,13 @@
   @DocsEditable
   String get tagName native "Element_tagName_Getter";
 
+  @DomName('Element.webkitInsertionParent')
+  @DocsEditable
+  @SupportedBrowser(SupportedBrowser.CHROME)
+  @SupportedBrowser(SupportedBrowser.SAFARI)
+  @Experimental
+  Node get insertionParent native "Element_webkitInsertionParent_Getter";
+
   @DomName('Element.webkitPseudo')
   @DocsEditable
   @SupportedBrowser(SupportedBrowser.CHROME)
@@ -17964,6 +17971,10 @@
   @DocsEditable
   void endOfStream(String error) native "MediaSource_endOfStream_Callback";
 
+  @DomName('MediaSource.isTypeSupported')
+  @DocsEditable
+  static bool isTypeSupported(String type) native "MediaSource_isTypeSupported_Callback";
+
   @DomName('MediaSource.removeEventListener')
   @DocsEditable
   void $dom_removeEventListener(String type, EventListener listener, [bool useCapture]) native "MediaSource_removeEventListener_Callback";
@@ -21593,18 +21604,10 @@
   @DocsEditable
   static const EventStreamProvider<RtcDataChannelEvent> dataChannelEvent = const EventStreamProvider<RtcDataChannelEvent>('datachannel');
 
-  @DomName('RTCPeerConnection.gatheringchangeEvent')
-  @DocsEditable
-  static const EventStreamProvider<Event> gatheringChangeEvent = const EventStreamProvider<Event>('gatheringchange');
-
   @DomName('RTCPeerConnection.icecandidateEvent')
   @DocsEditable
   static const EventStreamProvider<RtcIceCandidateEvent> iceCandidateEvent = const EventStreamProvider<RtcIceCandidateEvent>('icecandidate');
 
-  @DomName('RTCPeerConnection.icechangeEvent')
-  @DocsEditable
-  static const EventStreamProvider<Event> iceChangeEvent = const EventStreamProvider<Event>('icechange');
-
   @DomName('RTCPeerConnection.negotiationneededEvent')
   @DocsEditable
   static const EventStreamProvider<Event> negotiationNeededEvent = const EventStreamProvider<Event>('negotiationneeded');
@@ -21613,10 +21616,6 @@
   @DocsEditable
   static const EventStreamProvider<MediaStreamEvent> removeStreamEvent = const EventStreamProvider<MediaStreamEvent>('removestream');
 
-  @DomName('RTCPeerConnection.statechangeEvent')
-  @DocsEditable
-  static const EventStreamProvider<Event> stateChangeEvent = const EventStreamProvider<Event>('statechange');
-
   @DomName('RTCPeerConnection.RTCPeerConnection')
   @DocsEditable
   factory RtcPeerConnection(Map rtcIceServers, [Map mediaConstraints]) {
@@ -21638,10 +21637,6 @@
   @DocsEditable
   RtcSessionDescription get localDescription native "RTCPeerConnection_localDescription_Getter";
 
-  @DomName('RTCPeerConnection.readyState')
-  @DocsEditable
-  String get readyState native "RTCPeerConnection_readyState_Getter";
-
   @DomName('RTCPeerConnection.remoteDescription')
   @DocsEditable
   RtcSessionDescription get remoteDescription native "RTCPeerConnection_remoteDescription_Getter";
@@ -21746,18 +21741,10 @@
   @DocsEditable
   Stream<RtcDataChannelEvent> get onDataChannel => dataChannelEvent.forTarget(this);
 
-  @DomName('RTCPeerConnection.ongatheringchange')
-  @DocsEditable
-  Stream<Event> get onGatheringChange => gatheringChangeEvent.forTarget(this);
-
   @DomName('RTCPeerConnection.onicecandidate')
   @DocsEditable
   Stream<RtcIceCandidateEvent> get onIceCandidate => iceCandidateEvent.forTarget(this);
 
-  @DomName('RTCPeerConnection.onicechange')
-  @DocsEditable
-  Stream<Event> get onIceChange => iceChangeEvent.forTarget(this);
-
   @DomName('RTCPeerConnection.onnegotiationneeded')
   @DocsEditable
   Stream<Event> get onNegotiationNeeded => negotiationNeededEvent.forTarget(this);
@@ -21766,10 +21753,6 @@
   @DocsEditable
   Stream<MediaStreamEvent> get onRemoveStream => removeStreamEvent.forTarget(this);
 
-  @DomName('RTCPeerConnection.onstatechange')
-  @DocsEditable
-  Stream<Event> get onStateChange => stateChangeEvent.forTarget(this);
-
 }
 
 
@@ -21841,6 +21824,10 @@
   @DocsEditable
   DateTime get timestamp native "RTCStatsReport_timestamp_Getter";
 
+  @DomName('RTCStatsReport.type')
+  @DocsEditable
+  String get type native "RTCStatsReport_type_Getter";
+
   @DomName('RTCStatsReport.names')
   @DocsEditable
   List<String> names() native "RTCStatsReport_names_Callback";
@@ -23261,13 +23248,9 @@
 class SpeechRecognitionEvent extends Event {
   SpeechRecognitionEvent.internal() : super.internal();
 
-  @DomName('SpeechRecognitionEvent.result')
+  @DomName('SpeechRecognitionEvent.emma')
   @DocsEditable
-  SpeechRecognitionResult get result native "SpeechRecognitionEvent_result_Getter";
-
-  @DomName('SpeechRecognitionEvent.resultHistory')
-  @DocsEditable
-  List<SpeechRecognitionResult> get resultHistory native "SpeechRecognitionEvent_resultHistory_Getter";
+  Document get emma native "SpeechRecognitionEvent_emma_Getter";
 
   @DomName('SpeechRecognitionEvent.resultIndex')
   @DocsEditable
@@ -23966,6 +23949,13 @@
   factory Text(String data) => _TextFactoryProvider.createText(data);
   Text.internal() : super.internal();
 
+  @DomName('Text.webkitInsertionParent')
+  @DocsEditable
+  @SupportedBrowser(SupportedBrowser.CHROME)
+  @SupportedBrowser(SupportedBrowser.SAFARI)
+  @Experimental
+  Node get insertionParent native "Text_webkitInsertionParent_Getter";
+
   @DomName('Text.wholeText')
   @DocsEditable
   String get wholeText native "Text_wholeText_Getter";
@@ -26906,6 +26896,27 @@
 
 
 @DocsEditable
+@DomName('WebGLCompressedTexturePVRTC')
+class WebGLCompressedTexturePvrtc extends NativeFieldWrapperClass1 {
+  WebGLCompressedTexturePvrtc.internal();
+
+  static const int COMPRESSED_RGBA_PVRTC_2BPPV1_IMG = 0x8C03;
+
+  static const int COMPRESSED_RGBA_PVRTC_4BPPV1_IMG = 0x8C02;
+
+  static const int COMPRESSED_RGB_PVRTC_2BPPV1_IMG = 0x8C01;
+
+  static const int COMPRESSED_RGB_PVRTC_4BPPV1_IMG = 0x8C00;
+
+}
+// Copyright (c) 2012, 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.
+
+// WARNING: Do not edit - generated code.
+
+
+@DocsEditable
 @DomName('WebGLCompressedTextureS3TC')
 class WebGLCompressedTextureS3TC extends NativeFieldWrapperClass1 {
   WebGLCompressedTextureS3TC.internal();
@@ -29801,6 +29812,14 @@
   @DocsEditable
   int setTimeout(Object handler, int timeout) native "WorkerContext_setTimeout_Callback";
 
+  /**
+   * Access a sandboxed file system of the specified `size`. If `persistent` is
+   * true, the application will request permission from the user to create
+   * lasting storage. This storage cannot be freed without the user's
+   * permission. Returns a [Future] whose value stores a reference to the
+   * sandboxed file system for use. Because the file system is sandboxed,
+   * applications cannot access file systems created in other web pages. 
+   */
   @DomName('WorkerContext.webkitRequestFileSystem')
   @DocsEditable
   @SupportedBrowser(SupportedBrowser.CHROME)
@@ -29815,6 +29834,14 @@
     return completer.future;
   }
 
+  /**
+   * Access a sandboxed file system of the specified `size`. If `persistent` is
+   * true, the application will request permission from the user to create
+   * lasting storage. This storage cannot be freed without the user's
+   * permission. This call will block until a reference to the synchronous file 
+   * system API has been obtained. Because the file system is sandboxed,
+   * applications cannot access file systems created in other web pages. 
+   */
   @DomName('WorkerContext.webkitRequestFileSystemSync')
   @DocsEditable
   @SupportedBrowser(SupportedBrowser.CHROME)
@@ -29927,6 +29954,20 @@
   @DocsEditable
   String get userAgent native "WorkerNavigator_userAgent_Getter";
 
+  @DomName('WorkerNavigator.webkitPersistentStorage')
+  @DocsEditable
+  @SupportedBrowser(SupportedBrowser.CHROME)
+  @SupportedBrowser(SupportedBrowser.SAFARI)
+  @Experimental
+  StorageQuota get persistentStorage native "WorkerNavigator_webkitPersistentStorage_Getter";
+
+  @DomName('WorkerNavigator.webkitTemporaryStorage')
+  @DocsEditable
+  @SupportedBrowser(SupportedBrowser.CHROME)
+  @SupportedBrowser(SupportedBrowser.SAFARI)
+  @Experimental
+  StorageQuota get temporaryStorage native "WorkerNavigator_webkitTemporaryStorage_Getter";
+
 }
 // Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file
 // for details. All rights reserved. Use of this source code is governed by a
@@ -33522,17 +33563,10 @@
 
 
 /**
- * Works with KeyboardEvent and KeyEvent to determine how to expose information
- * about Key(board)Events. This class functions like an EventListenerList, and
- * provides a consistent interface for the Dart
- * user, despite the fact that a multitude of browsers that have varying
- * keyboard default behavior.
- *
- * This class is very much a work in progress, and we'd love to get information
- * on how we can make this class work with as many international keyboards as
- * possible. Bugs welcome!
+ * Internal class that does the actual calculations to determine keyCode and
+ * charCode for keydown, keypress, and keyup events for all browsers.
  */
-class KeyboardEventController {
+class _KeyboardEventHandler extends EventStreamProvider<KeyEvent> {
   // This code inspired by Closure's KeyHandling library.
   // http://closure-library.googlecode.com/svn/docs/closure_goog_events_keyhandler.js.source.html
 
@@ -33540,29 +33574,28 @@
    * The set of keys that have been pressed down without seeing their
    * corresponding keyup event.
    */
-  List<KeyboardEvent> _keyDownList;
-
-  /** The set of functions that wish to be notified when a KeyEvent happens. */
-  List<Function> _callbacks;
+  final List<KeyboardEvent> _keyDownList = <KeyboardEvent>[];
 
   /** The type of KeyEvent we are tracking (keyup, keydown, keypress). */
-  String _type;
+  final String _type;
 
   /** The element we are watching for events to happen on. */
-  EventTarget _target;
+  final EventTarget _target;
 
   // The distance to shift from upper case alphabet Roman letters to lower case.
-  final int _ROMAN_ALPHABET_OFFSET = "a".codeUnits[0] - "A".codeUnits[0];
+  static final int _ROMAN_ALPHABET_OFFSET = "a".codeUnits[0] - "A".codeUnits[0];
 
-  StreamSubscription _keyUpSubscription, _keyDownSubscription,
-      _keyPressSubscription;
+  /** Controller to produce KeyEvents for the stream. */
+  final StreamController _controller = new StreamController.broadcast();
+
+  static const _EVENT_TYPE = 'KeyEvent';
 
   /**
    * An enumeration of key identifiers currently part of the W3C draft for DOM3
    * and their mappings to keyCodes.
    * http://www.w3.org/TR/DOM-Level-3-Events/keyset.html#KeySet-Set
    */
-  static Map<String, int> _keyIdentifier = {
+  static const Map<String, int> _keyIdentifier = const {
     'Up': KeyCode.UP,
     'Down': KeyCode.DOWN,
     'Left': KeyCode.LEFT,
@@ -33588,53 +33621,48 @@
     'Insert': KeyCode.INSERT
   };
 
-  /** Named constructor to add an onKeyPress event listener to our handler. */
-  KeyboardEventController.keypress(EventTarget target) {
-    _KeyboardEventController(target, 'keypress');
+  /** Return a stream for KeyEvents for the specified target. */
+  Stream<KeyEvent> forTarget(EventTarget e, {bool useCapture: false}) {
+    return new _KeyboardEventHandler.initializeAllEventListeners(
+        _type, e).stream;
   }
 
-  /** Named constructor to add an onKeyUp event listener to our handler. */
-  KeyboardEventController.keyup(EventTarget target) {
-    _KeyboardEventController(target, 'keyup');
-  }
-
-  /** Named constructor to add an onKeyDown event listener to our handler. */
-  KeyboardEventController.keydown(EventTarget target) {
-    _KeyboardEventController(target, 'keydown');
+  /**
+   * Accessor to the stream associated with a particular KeyboardEvent
+   * EventTarget.
+   *
+   * [forTarget] must be called to initialize this stream to listen to a
+   * particular EventTarget.
+   */
+  Stream<KeyEvent> get stream {
+    if(_target != null) {
+      return _controller.stream;
+    } else {
+      throw new StateError("Not initialized. Call forTarget to access a stream "
+          "initialized with a particular EventTarget.");
+    }
   }
 
   /**
    * General constructor, performs basic initialization for our improved
    * KeyboardEvent controller.
    */
-  _KeyboardEventController(EventTarget target, String type) {
-    _callbacks = [];
-    _type = type;
-    _target = target;
+  _KeyboardEventHandler(this._type) :
+    _target = null, super(_EVENT_TYPE) {
   }
 
   /**
    * Hook up all event listeners under the covers so we can estimate keycodes
    * and charcodes when they are not provided.
    */
-  void _initializeAllEventListeners() {
-    _keyDownList = [];
-    if (_keyDownSubscription == null) {
-      _keyDownSubscription = Element.keyDownEvent.forTarget(
-          _target, useCapture: true).listen(processKeyDown);
-      _keyPressSubscription = Element.keyPressEvent.forTarget(
-          _target, useCapture: true).listen(processKeyUp);
-      _keyUpSubscription = Element.keyUpEvent.forTarget(
-          _target, useCapture: true).listen(processKeyPress);
-    }
-  }
-
-  /** Add a callback that wishes to be notified when a KeyEvent occurs. */
-  void add(void callback(KeyEvent)) {
-    if (_callbacks.length == 0) {
-      _initializeAllEventListeners();
-    }
-    _callbacks.add(callback);
+  _KeyboardEventHandler.initializeAllEventListeners(this._type, this._target) : 
+    super(_EVENT_TYPE) {
+    Element.keyDownEvent.forTarget(_target, useCapture: true).listen(
+        processKeyDown);
+    Element.keyPressEvent.forTarget(_target, useCapture: true).listen(
+        processKeyPress);
+    Element.keyUpEvent.forTarget(_target, useCapture: true).listen(
+        processKeyUp);
   }
 
   /**
@@ -33642,31 +33670,8 @@
    * occurred.
    */
   bool _dispatch(KeyEvent event) {
-    if (event.type == _type) {
-      // Make a copy of the listeners in case a callback gets removed while
-      // dispatching from the list.
-      List callbacksCopy = new List.from(_callbacks);
-      for(var callback in callbacksCopy) {
-        callback(event);
-      }
-    }
-  }
-
-  /** Remove the given callback from the listeners list. */
-  void remove(void callback(KeyEvent)) {
-    var index = _callbacks.indexOf(callback);
-    if (index != -1) {
-      _callbacks.removeAt(index);
-    }
-    if (_callbacks.length == 0) {
-      // If we have no listeners, don't bother keeping track of keypresses.
-      _keyDownSubscription.cancel();
-      _keyDownSubscription = null;
-      _keyPressSubscription.cancel();
-      _keyPressSubscription = null;
-      _keyUpSubscription.cancel();
-      _keyUpSubscription = null;
-    }
+    if (event.type == _type)
+      _controller.add(event);
   }
 
   /** Determine if caps lock is one of the currently depressed keys. */
@@ -33854,7 +33859,7 @@
          _keyDownList.last.keyCode == KeyCode.ALT && !e.altKey ||
          Device.userAgent.contains('Mac') &&
          _keyDownList.last.keyCode == KeyCode.META && !e.metaKey)) {
-      _keyDownList = [];
+      _keyDownList.clear();
     }
 
     var event = new KeyEvent(e);
@@ -33914,8 +33919,7 @@
       }
     }
     if (toRemove != null) {
-      _keyDownList =
-          _keyDownList.where((element) => element != toRemove).toList();
+      _keyDownList.removeWhere((element) => element == toRemove);
     } else if (_keyDownList.length > 0) {
       // This happens when we've reached some international keyboard case we
       // haven't accounted for or we haven't correctly eliminated all browser
@@ -33925,6 +33929,37 @@
     _dispatch(e);
   }
 }
+
+
+/**
+ * Records KeyboardEvents that occur on a particular element, and provides a
+ * stream of outgoing KeyEvents with cross-browser consistent keyCode and
+ * charCode values despite the fact that a multitude of browsers that have
+ * varying keyboard default behavior.
+ *
+ * Example usage:
+ *
+ *     KeyboardEventStream.onKeyDown(document.body).listen(
+ *         keydownHandlerTest);
+ *
+ * This class is very much a work in progress, and we'd love to get information
+ * on how we can make this class work with as many international keyboards as
+ * possible. Bugs welcome!
+ */
+class KeyboardEventStream {
+
+  /** Named constructor to produce a stream for onKeyPress events. */
+  static Stream<KeyEvent> onKeyPress(EventTarget target) =>
+      new _KeyboardEventHandler('keypress').forTarget(target);
+
+  /** Named constructor to produce a stream for onKeyUp events. */
+  static Stream<KeyEvent> onKeyUp(EventTarget target) =>
+      new _KeyboardEventHandler('keyup').forTarget(target);
+
+  /** Named constructor to produce a stream for onKeyDown events. */
+  static Stream<KeyEvent> onKeyDown(EventTarget target) =>
+    new _KeyboardEventHandler('keydown').forTarget(target);
+}
 // Copyright (c) 2012, 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.
@@ -35042,6 +35077,39 @@
   timer = new _Timer(() { canceller(id); });
   return timer;
 };
+
+class _PureIsolateTimer implements Timer {
+  final ReceivePort _port = new ReceivePort();
+  SendPort _sendPort; // Effectively final.
+
+  _PureIsolateTimer(int milliSeconds, callback, repeating) {
+    _sendPort = _port.toSendPort();
+    _port.receive((msg, replyTo) {
+      assert(msg == _TIMER_PING);
+      assert(replyTo == _HELPER_ISOLATE_PORT);
+      callback(this);
+      if (!repeating) _cancel();
+    });
+    _HELPER_ISOLATE_PORT.then((port) {
+      port.send([_NEW_TIMER, milliSeconds, repeating], _sendPort);
+    });
+  }
+
+  void cancel() {
+    _cancel();
+    _HELPER_ISOLATE_PORT.then((port) {
+      port.send([_CANCEL_TIMER], _sendPort);
+    });
+  }
+
+  void _cancel() {
+    _port.close();
+  }
+}
+
+get _pureIsolateTimerFactoryClosure =>
+    ((int milliSeconds, void callback(Timer time), bool repeating) =>
+        new _PureIsolateTimer(milliSeconds, callback, repeating));
 // Copyright (c) 2013, 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.
@@ -35272,6 +35340,9 @@
  * inconsistencies, and also provide both keyCode and charCode information
  * for all key events (when such information can be determined).
  *
+ * KeyEvent tries to provide a higher level, more polished keyboard event
+ * information on top of the "raw" [KeyboardEvent].
+ *
  * This class is very much a work in progress, and we'd love to get information
  * on how we can make this class work with as many international keyboards as
  * possible. Bugs welcome!
@@ -35310,7 +35381,7 @@
   /** Accessor to the underlying altKey value is the parent event. */
   bool get _realAltKey => _parent.altKey;
 
-  /** Construct a KeyEvent with [parent] as event we're emulating. */
+  /** Construct a KeyEvent with [parent] as the event we're emulating. */
   KeyEvent(KeyboardEvent parent) {
     _parent = parent;
     _shadowAltKey = _realAltKey;
@@ -35318,6 +35389,16 @@
     _shadowKeyCode = _realKeyCode;
   }
 
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyDownEvent =
+    new _KeyboardEventHandler('keydown');
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyUpEvent =
+    new _KeyboardEventHandler('keyup');
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyPressEvent =
+    new _KeyboardEventHandler('keypress');
+
   /** True if the altGraphKey is pressed during this event. */
   bool get altGraphKey => _parent.altGraphKey;
   bool get bubbles => _parent.bubbles;
@@ -35526,7 +35607,7 @@
 // The receiver is JS.
 class _JsSendPortSync implements SendPortSync {
 
-  num _id;
+  final num _id;
   _JsSendPortSync(this._id);
 
   callSync(var message) {
@@ -35696,7 +35777,7 @@
  */
 abstract class _MicrotaskScheduler {
   bool _nextMicrotaskFrameScheduled = false;
-  _MicrotaskCallback _callback;
+  final _MicrotaskCallback _callback;
 
   _MicrotaskScheduler(this._callback);
 
@@ -36079,7 +36160,17 @@
 
 
 // This API is exploratory.
-spawnDomFunction(Function topLevelFunction) => _Utils.spawnDomFunctionImpl(topLevelFunction);
+Future<SendPort> spawnDomFunction(Function topLevelFunction) {
+  final completer = new Completer<SendPort>();
+  final port = new ReceivePort();
+  port.receive((result, _) {
+    completer.complete(result);
+    port.close();
+  });
+  // TODO: SendPort.hashCode is ugly way to access port id.
+  _Utils.spawnDomFunction(topLevelFunction, port.toSendPort().hashCode);
+  return completer.future;
+}
 
 // testRunner implementation.
 // FIXME: provide a separate lib for testRunner.
@@ -36135,6 +36226,18 @@
     return result;
   }
 
+  static int convertCanvasElementGetContextMap(Map map) {
+    int result = 0;
+    if (map['alpha'] == true) result |= 0x01;
+    if (map['depth'] == true) result |= 0x02;
+    if (map['stencil'] == true) result |= 0x4;
+    if (map['antialias'] == true) result |= 0x08;
+    if (map['premultipliedAlpha'] == true) result |= 0x10;
+    if (map['preserveDrawingBuffer'] == true) result |= 0x20;
+
+    return result;
+  }
+
   static void populateMap(Map result, List list) {
     for (int i = 0; i < list.length; i += 2) {
       result[list[i]] = list[i + 1];
@@ -36150,9 +36253,8 @@
   }
 
   static window() native "Utils_window";
-  static print(String message) native "Utils_print";
   static forwardingPrint(String message) native "Utils_forwardingPrint";
-  static SendPort spawnDomFunctionImpl(Function topLevelFunction) native "Utils_spawnDomFunction";
+  static void spawnDomFunction(Function topLevelFunction, int replyTo) native "Utils_spawnDomFunction";
   static int _getNewIsolateId() native "Utils_getNewIsolateId";
   static bool shadowRootSupported(Document document) native "Utils_shadowRootSupported";
 }
@@ -36224,12 +36326,41 @@
   bool get isEmpty => Maps.isEmpty(this);
 }
 
-get _printClosure => (s) {
-  try {
-    window.console.log(s);
-  } catch (_) {
-    _Utils.print(s);
-  }
+final Future<SendPort> _HELPER_ISOLATE_PORT =
+    spawnDomFunction(_helperIsolateMain);
+
+final _TIMER_REGISTRY = new Map<SendPort, Timer>();
+
+const _NEW_TIMER = 'NEW_TIMER';
+const _CANCEL_TIMER = 'CANCEL_TIMER';
+const _TIMER_PING = 'TIMER_PING';
+const _PRINT = 'PRINT';
+
+_helperIsolateMain() {
+  port.receive((msg, replyTo) {
+    final cmd = msg[0];
+    if (cmd == _NEW_TIMER) {
+      final duration = new Duration(milliseconds: msg[1]);
+      bool periodic = msg[2];
+      final callback = () { replyTo.send(_TIMER_PING); };
+      _TIMER_REGISTRY[replyTo] = periodic ?
+          new Timer.periodic(duration, callback) :
+          new Timer(duration, callback);
+    } else if (cmd == _CANCEL_TIMER) {
+      _TIMER_REGISTRY.remove(replyTo).cancel();
+    } else if (cmd == _PRINT) {
+      final message = msg[1];
+      // TODO(antonm): we need somehow identify those isolates.
+      print('[From isolate] $message');
+    }
+  });
+}
+
+final _printClosure = window.console.log;
+final _pureIsolatePrintClosure = (s) {
+  _HELPER_ISOLATE_PORT.then((sendPort) {
+    sendPort.send([_PRINT, s]);
+  });
 };
 
 final _forwardingPrintClosure = _Utils.forwardingPrint;
diff --git a/sdk/lib/isolate/base.dart b/sdk/lib/isolate/base.dart
deleted file mode 100644
index 519cf49..0000000
--- a/sdk/lib/isolate/base.dart
+++ /dev/null
@@ -1,207 +0,0 @@
-// Copyright (c) 2012, 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 dart.isolate;
-
-class IsolateSpawnException implements Exception {
-  const IsolateSpawnException(String this._s);
-  String toString() => "IsolateSpawnException: '$_s'";
-  final String _s;
-}
-
-/**
- * The initial [ReceivePort] available by default for this isolate. This
- * [ReceivePort] is created automatically and it is commonly used to establish
- * the first communication between isolates (see [spawnFunction] and
- * [spawnUri]).
- */
-ReceivePort get port => _Isolate.port;
-
-/**
- * Creates and spawns an isolate that shares the same code as the current
- * isolate, but that starts from [topLevelFunction]. The [topLevelFunction]
- * argument must be a static top-level function or a static method that takes no
- * arguments. It is illegal to pass a function closure.
- *
- * When any isolate starts (even the main script of the application), a default
- * [ReceivePort] is created for it. This port is available from the top-level
- * getter [port] defined in this library.
- *
- * [spawnFunction] returns a [SendPort] derived from the child isolate's default
- * port.
- *
- * The optional [unhandledExceptionCallback] argument is invoked whenever an
- * exception inside the isolate is unhandled. It can be seen as a big
- * `try/catch` around everything that is executed inside the isolate. The
- * callback should return `true` when it was able to handled the exception.
- *
- * See comments at the top of this library for more details.
- */
-SendPort spawnFunction(void topLevelFunction(),
-    [bool unhandledExceptionCallback(IsolateUnhandledException e)])
-    => _Isolate.spawnFunction(topLevelFunction, unhandledExceptionCallback);
-
-/**
- * Creates and spawns an isolate whose code is available at [uri].  Like with
- * [spawnFunction], the child isolate will have a default [ReceivePort], and a
- * this function returns a [SendPort] derived from it.
- *
- * See comments at the top of this library for more details.
- */
-SendPort spawnUri(String uri) => _Isolate.spawnUri(uri);
-
-/**
- * [SendPort]s are created from [ReceivePort]s. Any message sent through
- * a [SendPort] is delivered to its respective [ReceivePort]. There might be
- * many [SendPort]s for the same [ReceivePort].
- *
- * [SendPort]s can be transmitted to other isolates.
- */
-abstract class SendPort {
-
-  /**
-   * Sends an asynchronous [message] to this send port. The message is copied to
-   * the receiving isolate. If specified, the [replyTo] port will be provided to
-   * the receiver to facilitate exchanging sequences of messages.
-   *
-   * The content of [message] can be: primitive values (null, num, bool, double,
-   * String), instances of [SendPort], and lists and maps whose elements are any
-   * of these. List and maps are also allowed to be cyclic.
-   *
-   * In the special circumstances when two isolates share the same code and are
-   * running in the same process (e.g. isolates created via [spawnFunction]), it
-   * is also possible to send object instances (which would be copied in the
-   * process). This is currently only supported by the dartvm.  For now, the
-   * dart2js compiler only supports the restricted messages described above.
-   *
-   * Deprecation note: it is no longer valid to transmit a [ReceivePort] in a
-   * message. Previously they were translated to the corresponding send port
-   * before being transmitted.
-   */
-  void send(var message, [SendPort replyTo]);
-
-  /**
-   * Sends a message to this send port and returns a [Future] of the reply.
-   * Basically, this internally creates a new receive port, sends a
-   * message to this send port with replyTo set to such receive port, and, when
-   * a reply is received, it closes the receive port and completes the returned
-   * future.
-   */
-  Future call(var message);
-
-  /**
-   * Tests whether [other] is a [SendPort] pointing to the same
-   * [ReceivePort] as this one.
-   */
-  bool operator==(var other);
-
-  /**
-   * Returns an immutable hash code for this send port that is
-   * consistent with the == operator.
-   */
-  int get hashCode;
-
-}
-
-/**
- * [ReceivePort]s, together with [SendPort]s, are the only means of
- * communication between isolates. [ReceivePort]s have a [:toSendPort:] method
- * which returns a [SendPort]. Any message that is sent through this [SendPort]
- * is delivered to the [ReceivePort] it has been created from. There, they are
- * dispatched to the callback that has been registered on the receive port.
- *
- * A [ReceivePort] may have many [SendPort]s.
- */
-abstract class ReceivePort {
-
-  /**
-   * Opens a long-lived port for receiving messages. The returned port
-   * must be explicitly closed through [ReceivePort.close].
-   */
-  external factory ReceivePort();
-
-  /**
-   * Sets up a callback function for receiving pending or future
-   * messages on this receive port.
-   */
-  void receive(void callback(var message, SendPort replyTo));
-
-  /**
-   * Closes this receive port immediately. Pending messages will not
-   * be processed and it is impossible to re-open the port. Single-shot
-   * reply ports, such as those created through [SendPort.call], are
-   * automatically closed when the reply has been received. Multiple
-   * invocations of [close] are allowed but ignored.
-   */
-  void close();
-
-  /**
-   * Creates a new send port that sends to this receive port. It is legal to
-   * create several [SendPort]s from the same [ReceivePort].
-   */
-  SendPort toSendPort();
-
-}
-
-/**
- * [SendPortSync]s are created from [ReceivePortSync]s. Any message sent through
- * a [SendPortSync] is delivered to its respective [ReceivePortSync]. There
- * might be many [SendPortSync]s for the same [ReceivePortSync].
- *
- * [SendPortSync]s can be transmitted to other isolates.
- */
-abstract class SendPortSync {
-  /**
-   * Sends a synchronous message to this send port and returns the result.
-   */
-  callSync(var message);
-
-  /**
-   * Tests whether [other] is a [SendPortSync] pointing to the same
-   * [ReceivePortSync] as this one.
-   */
-  bool operator==(var other);
-
-  /**
-   * Returns an immutable hash code for this send port that is
-   * consistent with the == operator.
-   */
-  int get hashCode;
-}
-
-// The VM doesn't support accessing external globals in the same library. We
-// therefore create this wrapper class.
-// TODO(6997): Don't go through static class for external variables.
-abstract class _Isolate {
-  external static ReceivePort get port;
-  external static SendPort spawnFunction(void topLevelFunction(),
-    [bool unhandledExceptionCallback(IsolateUnhandledException e)]);
-  external static SendPort spawnUri(String uri);
-}
-
-/**
- * Wraps unhandled exceptions thrown during isolate execution. It is
- * used to show both the error message and the stack trace for unhandled
- * exceptions.
- */
-class IsolateUnhandledException implements Exception {
-  /** Message being handled when exception occurred. */
-  final message;
-
-  /** Wrapped exception. */
-  final source;
-
-  /** Trace for the wrapped exception. */
-  final Object stackTrace;
-
-  const IsolateUnhandledException(this.message, this.source, this.stackTrace);
-
-  String toString() {
-    return 'IsolateUnhandledException: exception while handling message: '
-        '${message} \n  '
-        '${source.toString().replaceAll("\n", "\n  ")}\n'
-        'original stack trace:\n  '
-        '${stackTrace.toString().replaceAll("\n","\n  ")}';
-  }
-}
diff --git a/sdk/lib/isolate/isolate.dart b/sdk/lib/isolate/isolate.dart
index 0b57f15..49c0eb8 100644
--- a/sdk/lib/isolate/isolate.dart
+++ b/sdk/lib/isolate/isolate.dart
@@ -6,5 +6,202 @@
 
 import "dart:async";
 
-part "base.dart";
 part "isolate_stream.dart";
+
+class IsolateSpawnException implements Exception {
+  const IsolateSpawnException(String this._s);
+  String toString() => "IsolateSpawnException: '$_s'";
+  final String _s;
+}
+
+/**
+ * The initial [ReceivePort] available by default for this isolate. This
+ * [ReceivePort] is created automatically and it is commonly used to establish
+ * the first communication between isolates (see [spawnFunction] and
+ * [spawnUri]).
+ */
+ReceivePort get port => _Isolate.port;
+
+/**
+ * Creates and spawns an isolate that shares the same code as the current
+ * isolate, but that starts from [topLevelFunction]. The [topLevelFunction]
+ * argument must be a static top-level function or a static method that takes no
+ * arguments. It is illegal to pass a function closure.
+ *
+ * When any isolate starts (even the main script of the application), a default
+ * [ReceivePort] is created for it. This port is available from the top-level
+ * getter [port] defined in this library.
+ *
+ * [spawnFunction] returns a [SendPort] derived from the child isolate's default
+ * port.
+ *
+ * The optional [unhandledExceptionCallback] argument is invoked whenever an
+ * exception inside the isolate is unhandled. It can be seen as a big
+ * `try/catch` around everything that is executed inside the isolate. The
+ * callback should return `true` when it was able to handled the exception.
+ */
+SendPort spawnFunction(void topLevelFunction(),
+    [bool unhandledExceptionCallback(IsolateUnhandledException e)])
+    => _Isolate.spawnFunction(topLevelFunction, unhandledExceptionCallback);
+
+/**
+ * Creates and spawns an isolate whose code is available at [uri].  Like with
+ * [spawnFunction], the child isolate will have a default [ReceivePort], and a
+ * this function returns a [SendPort] derived from it.
+ */
+SendPort spawnUri(String uri) => _Isolate.spawnUri(uri);
+
+/**
+ * [SendPort]s are created from [ReceivePort]s. Any message sent through
+ * a [SendPort] is delivered to its respective [ReceivePort]. There might be
+ * many [SendPort]s for the same [ReceivePort].
+ *
+ * [SendPort]s can be transmitted to other isolates.
+ */
+abstract class SendPort {
+
+  /**
+   * Sends an asynchronous [message] to this send port. The message is copied to
+   * the receiving isolate. If specified, the [replyTo] port will be provided to
+   * the receiver to facilitate exchanging sequences of messages.
+   *
+   * The content of [message] can be: primitive values (null, num, bool, double,
+   * String), instances of [SendPort], and lists and maps whose elements are any
+   * of these. List and maps are also allowed to be cyclic.
+   *
+   * In the special circumstances when two isolates share the same code and are
+   * running in the same process (e.g. isolates created via [spawnFunction]), it
+   * is also possible to send object instances (which would be copied in the
+   * process). This is currently only supported by the dartvm.  For now, the
+   * dart2js compiler only supports the restricted messages described above.
+   *
+   * Deprecation note: it is no longer valid to transmit a [ReceivePort] in a
+   * message. Previously they were translated to the corresponding send port
+   * before being transmitted.
+   */
+  void send(var message, [SendPort replyTo]);
+
+  /**
+   * Sends a message to this send port and returns a [Future] of the reply.
+   * Basically, this internally creates a new receive port, sends a
+   * message to this send port with replyTo set to such receive port, and, when
+   * a reply is received, it closes the receive port and completes the returned
+   * future.
+   */
+  Future call(var message);
+
+  /**
+   * Tests whether [other] is a [SendPort] pointing to the same
+   * [ReceivePort] as this one.
+   */
+  bool operator==(var other);
+
+  /**
+   * Returns an immutable hash code for this send port that is
+   * consistent with the == operator.
+   */
+  int get hashCode;
+
+}
+
+/**
+ * [ReceivePort]s, together with [SendPort]s, are the only means of
+ * communication between isolates. [ReceivePort]s have a [:toSendPort:] method
+ * which returns a [SendPort]. Any message that is sent through this [SendPort]
+ * is delivered to the [ReceivePort] it has been created from. There, they are
+ * dispatched to the callback that has been registered on the receive port.
+ *
+ * A [ReceivePort] may have many [SendPort]s.
+ */
+abstract class ReceivePort {
+
+  /**
+   * Opens a long-lived port for receiving messages. The returned port
+   * must be explicitly closed through [ReceivePort.close].
+   */
+  external factory ReceivePort();
+
+  /**
+   * Sets up a callback function for receiving pending or future
+   * messages on this receive port.
+   */
+  void receive(void callback(var message, SendPort replyTo));
+
+  /**
+   * Closes this receive port immediately. Pending messages will not
+   * be processed and it is impossible to re-open the port. Single-shot
+   * reply ports, such as those created through [SendPort.call], are
+   * automatically closed when the reply has been received. Multiple
+   * invocations of [close] are allowed but ignored.
+   */
+  void close();
+
+  /**
+   * Creates a new send port that sends to this receive port. It is legal to
+   * create several [SendPort]s from the same [ReceivePort].
+   */
+  SendPort toSendPort();
+
+}
+
+/**
+ * [SendPortSync]s are created from [ReceivePortSync]s. Any message sent through
+ * a [SendPortSync] is delivered to its respective [ReceivePortSync]. There
+ * might be many [SendPortSync]s for the same [ReceivePortSync].
+ *
+ * [SendPortSync]s can be transmitted to other isolates.
+ */
+abstract class SendPortSync {
+  /**
+   * Sends a synchronous message to this send port and returns the result.
+   */
+  callSync(var message);
+
+  /**
+   * Tests whether [other] is a [SendPortSync] pointing to the same
+   * [ReceivePortSync] as this one.
+   */
+  bool operator==(var other);
+
+  /**
+   * Returns an immutable hash code for this send port that is
+   * consistent with the == operator.
+   */
+  int get hashCode;
+}
+
+// The VM doesn't support accessing external globals in the same library. We
+// therefore create this wrapper class.
+// TODO(6997): Don't go through static class for external variables.
+abstract class _Isolate {
+  external static ReceivePort get port;
+  external static SendPort spawnFunction(void topLevelFunction(),
+    [bool unhandledExceptionCallback(IsolateUnhandledException e)]);
+  external static SendPort spawnUri(String uri);
+}
+
+/**
+ * Wraps unhandled exceptions thrown during isolate execution. It is
+ * used to show both the error message and the stack trace for unhandled
+ * exceptions.
+ */
+class IsolateUnhandledException implements Exception {
+  /** Message being handled when exception occurred. */
+  final message;
+
+  /** Wrapped exception. */
+  final source;
+
+  /** Trace for the wrapped exception. */
+  final Object stackTrace;
+
+  const IsolateUnhandledException(this.message, this.source, this.stackTrace);
+
+  String toString() {
+    return 'IsolateUnhandledException: exception while handling message: '
+        '${message} \n  '
+        '${source.toString().replaceAll("\n", "\n  ")}\n'
+        'original stack trace:\n  '
+        '${stackTrace.toString().replaceAll("\n","\n  ")}';
+  }
+}
diff --git a/sdk/lib/isolate/isolate_sources.gypi b/sdk/lib/isolate/isolate_sources.gypi
index 2fa168c..fdc0f95 100644
--- a/sdk/lib/isolate/isolate_sources.gypi
+++ b/sdk/lib/isolate/isolate_sources.gypi
@@ -6,7 +6,6 @@
   'sources': [
     'isolate.dart',
     # The above file needs to be first as it lists the parts below.
-    'base.dart',
     'isolate_stream.dart',
   ],
 }
diff --git a/sdk/lib/isolate/isolate_stream.dart b/sdk/lib/isolate/isolate_stream.dart
index 9a735c9..a48c44d 100644
--- a/sdk/lib/isolate/isolate_stream.dart
+++ b/sdk/lib/isolate/isolate_stream.dart
@@ -145,8 +145,6 @@
  * exception inside the isolate is unhandled. It can be seen as a big
  * `try/catch` around everything that is executed inside the isolate. The
  * callback should return `true` when it was able to handled the exception.
- *
- * See comments at the top of this library for more details.
  */
 external IsolateSink streamSpawnFunction(
     void topLevelFunction(),
diff --git a/sdk/lib/json/json.dart b/sdk/lib/json/json.dart
index 17147e1..8568d13 100644
--- a/sdk/lib/json/json.dart
+++ b/sdk/lib/json/json.dart
@@ -4,4 +4,804 @@
 
 library dart.json;
 
-part 'json_base.dart';
+// JSON parsing and serialization.
+
+/**
+ * Error thrown by JSON serialization if an object cannot be serialized.
+ *
+ * The [unsupportedObject] field holds that object that failed to be serialized.
+ *
+ * If an object isn't directly serializable, the serializer calls the 'toJson'
+ * method on the object. If that call fails, the error will be stored in the
+ * [cause] field. If the call returns an object that isn't directly
+ * serializable, the [cause] will be null.
+ */
+class JsonUnsupportedObjectError implements Error {
+  /** The object that could not be serialized. */
+  final unsupportedObject;
+  /** The exception thrown by object's [:toJson:] method, if any. */
+  final cause;
+  JsonUnsupportedObjectError(this.unsupportedObject) : cause = null;
+  JsonUnsupportedObjectError.withCause(this.unsupportedObject, this.cause);
+
+  String toString() {
+    if (cause != null) {
+      return "Calling toJson method on object failed.";
+    } else {
+      return "Object toJson method returns non-serializable value.";
+    }
+  }
+}
+
+
+/**
+ * Parses [json] and build the corresponding parsed JSON value.
+ *
+ * Parsed JSON values are of the types [num], [String], [bool], [Null],
+ * [List]s of parsed JSON values or [Map]s from [String] to parsed
+ * JSON values.
+ *
+ * The optional [revivier] function, if provided, is called once for each
+ * object or list property parsed. The arguments are the property name
+ * ([String]) or list index ([int]), and the value is the parsed value.
+ * The return value of the revivier will be used as the value of that property
+ * instead the parsed value.
+ *
+ * Throws [FormatException] if the input is not valid JSON text.
+ */
+external parse(String json, [reviver(var key, var value)]);
+
+_parse(String json, reviver(var key, var value)) {
+  BuildJsonListener listener;
+  if (reviver == null) {
+    listener = new BuildJsonListener();
+  } else {
+    listener = new ReviverJsonListener(reviver);
+  }
+  new JsonParser(json, listener).parse();
+  return listener.result;
+}
+
+/**
+ * Serializes [object] into a JSON string.
+ *
+ * Directly serializable types are [num], [String], [bool], [Null], [List]
+ * and [Map].
+ * For [List], the elements must all be serializable.
+ * For [Map], the keys must be [String] and the values must be serializable.
+ * If a value is any other type is attempted serialized, a "toJson()" method
+ * is invoked on the object and the result, which must be a directly
+ * serializable type, is serialized instead of the original value.
+ * If the object does not support this method, throws, or returns a
+ * value that is not directly serializable, a [JsonUnsupportedObjectError]
+ * exception is thrown. If the call throws (including the case where there
+ * is no nullary "toJson" method, the error is caught and stored in the
+ * [JsonUnsupportedObjectError]'s [:cause:] field.
+ *Json
+ * Objects should not change during serialization.
+ * If an object is serialized more than once, [stringify] is allowed to cache
+ * the JSON text for it. I.e., if an object changes after it is first
+ * serialized, the new values may or may not be reflected in the result.
+ */
+String stringify(Object object) {
+  return _JsonStringifier.stringify(object);
+}
+
+/**
+ * Serializes [object] into [output] stream.
+ *
+ * Performs the same operations as [stringify] but outputs the resulting
+ * string to an existing [StringBuffer] instead of creating a new [String].
+ *
+ * If serialization fails by throwing, some data might have been added to
+ * [output], but it won't contain valid JSON text.
+ */
+void printOn(Object object, StringBuffer output) {
+  return _JsonStringifier.printOn(object, output);
+}
+
+//// Implementation ///////////////////////////////////////////////////////////
+
+// Simple API for JSON parsing.
+
+abstract class JsonListener {
+  void handleString(String value) {}
+  void handleNumber(num value) {}
+  void handleBool(bool value) {}
+  void handleNull() {}
+  void beginObject() {}
+  void propertyName() {}
+  void propertyValue() {}
+  void endObject() {}
+  void beginArray() {}
+  void arrayElement() {}
+  void endArray() {}
+  /** Called on failure to parse [source]. */
+  void fail(String source, int position, String message) {}
+}
+
+/**
+ * A [JsonListener] that builds data objects from the parser events.
+ *
+ * This is a simple stack-based object builder. It keeps the most recently
+ * seen value in a variable, and uses it depending on the following event.
+ */
+class BuildJsonListener extends JsonListener {
+  /**
+   * Stack used to handle nested containers.
+   *
+   * The current container is pushed on the stack when a new one is
+   * started. If the container is a [Map], there is also a current [key]
+   * which is also stored on the stack.
+   */
+  List stack = [];
+  /** The current [Map] or [List] being built. */
+  var currentContainer;
+  /** The most recently read property key. */
+  String key;
+  /** The most recently read value. */
+  var value;
+
+  /** Pushes the currently active container (and key, if a [Map]). */
+  void pushContainer() {
+    if (currentContainer is Map) stack.add(key);
+    stack.add(currentContainer);
+  }
+
+  /** Pops the top container from the [stack], including a key if applicable. */
+  void popContainer() {
+    value = currentContainer;
+    currentContainer = stack.removeLast();
+    if (currentContainer is Map) key = stack.removeLast();
+  }
+
+  void handleString(String value) { this.value = value; }
+  void handleNumber(num value) { this.value = value; }
+  void handleBool(bool value) { this.value = value; }
+  void handleNull() { this.value = value; }
+
+  void beginObject() {
+    pushContainer();
+    currentContainer = {};
+  }
+
+  void propertyName() {
+    key = value;
+    value = null;
+  }
+
+  void propertyValue() {
+    Map map = currentContainer;
+    map[key] = value;
+    key = value = null;
+  }
+
+  void endObject() {
+    popContainer();
+  }
+
+  void beginArray() {
+    pushContainer();
+    currentContainer = [];
+  }
+
+  void arrayElement() {
+    List list = currentContainer;
+    currentContainer.add(value);
+    value = null;
+  }
+
+  void endArray() {
+    popContainer();
+  }
+
+  /** Read out the final result of parsing a JSON string. */
+  get result {
+    assert(currentContainer == null);
+    return value;
+  }
+}
+
+typedef _Reviver(var key, var value);
+
+class ReviverJsonListener extends BuildJsonListener {
+  final _Reviver reviver;
+  ReviverJsonListener(reviver(key, value)) : this.reviver = reviver;
+
+  void arrayElement() {
+    List list = currentContainer;
+    value = reviver(list.length, value);
+    super.arrayElement();
+  }
+
+  void propertyValue() {
+    value = reviver(key, value);
+    super.propertyValue();
+  }
+
+  get result {
+    return reviver("", value);
+  }
+}
+
+class JsonParser {
+  // A simple non-recursive state-based parser for JSON.
+  //
+  // Literal values accepted in states ARRAY_EMPTY, ARRAY_COMMA, OBJECT_COLON
+  // and strings also in OBJECT_EMPTY, OBJECT_COMMA.
+  //               VALUE  STRING  :  ,  }  ]        Transitions to
+  // EMPTY            X      X                   -> END
+  // ARRAY_EMPTY      X      X             @     -> ARRAY_VALUE / pop
+  // ARRAY_VALUE                     @     @     -> ARRAY_COMMA / pop
+  // ARRAY_COMMA      X      X                   -> ARRAY_VALUE
+  // OBJECT_EMPTY            X          @        -> OBJECT_KEY / pop
+  // OBJECT_KEY                   @              -> OBJECT_COLON
+  // OBJECT_COLON     X      X                   -> OBJECT_VALUE
+  // OBJECT_VALUE                    @  @        -> OBJECT_COMMA / pop
+  // OBJECT_COMMA            X                   -> OBJECT_KEY
+  // END
+  // Starting a new array or object will push the current state. The "pop"
+  // above means restoring this state and then marking it as an ended value.
+  // X means generic handling, @ means special handling for just that
+  // state - that is, values are handled generically, only punctuation
+  // cares about the current state.
+  // Values for states are chosen so bits 0 and 1 tell whether
+  // a string/value is allowed, and setting bits 0 through 2 after a value
+  // gets to the next state (not empty, doesn't allow a value).
+
+  // State building-block constants.
+  static const int INSIDE_ARRAY = 1;
+  static const int INSIDE_OBJECT = 2;
+  static const int AFTER_COLON = 3;  // Always inside object.
+
+  static const int ALLOW_STRING_MASK = 8;  // Allowed if zero.
+  static const int ALLOW_VALUE_MASK = 4;  // Allowed if zero.
+  static const int ALLOW_VALUE = 0;
+  static const int STRING_ONLY = 4;
+  static const int NO_VALUES = 12;
+
+  // Objects and arrays are "empty" until their first property/element.
+  static const int EMPTY = 0;
+  static const int NON_EMPTY = 16;
+  static const int EMPTY_MASK = 16;  // Empty if zero.
+
+
+  static const int VALUE_READ_BITS = NO_VALUES | NON_EMPTY;
+
+  // Actual states.
+  static const int STATE_INITIAL      = EMPTY | ALLOW_VALUE;
+  static const int STATE_END          = NON_EMPTY | NO_VALUES;
+
+  static const int STATE_ARRAY_EMPTY  = INSIDE_ARRAY | EMPTY | ALLOW_VALUE;
+  static const int STATE_ARRAY_VALUE  = INSIDE_ARRAY | NON_EMPTY | NO_VALUES;
+  static const int STATE_ARRAY_COMMA  = INSIDE_ARRAY | NON_EMPTY | ALLOW_VALUE;
+
+  static const int STATE_OBJECT_EMPTY = INSIDE_OBJECT | EMPTY | STRING_ONLY;
+  static const int STATE_OBJECT_KEY   = INSIDE_OBJECT | NON_EMPTY | NO_VALUES;
+  static const int STATE_OBJECT_COLON = AFTER_COLON | NON_EMPTY | ALLOW_VALUE;
+  static const int STATE_OBJECT_VALUE = AFTER_COLON | NON_EMPTY | NO_VALUES;
+  static const int STATE_OBJECT_COMMA = INSIDE_OBJECT | NON_EMPTY | STRING_ONLY;
+
+  // Character code constants.
+  static const int BACKSPACE       = 0x08;
+  static const int TAB             = 0x09;
+  static const int NEWLINE         = 0x0a;
+  static const int CARRIAGE_RETURN = 0x0d;
+  static const int FORM_FEED       = 0x0c;
+  static const int SPACE           = 0x20;
+  static const int QUOTE           = 0x22;
+  static const int PLUS            = 0x2b;
+  static const int COMMA           = 0x2c;
+  static const int MINUS           = 0x2d;
+  static const int DECIMALPOINT    = 0x2e;
+  static const int SLASH           = 0x2f;
+  static const int CHAR_0          = 0x30;
+  static const int CHAR_9          = 0x39;
+  static const int COLON           = 0x3a;
+  static const int CHAR_E          = 0x45;
+  static const int LBRACKET        = 0x5b;
+  static const int BACKSLASH       = 0x5c;
+  static const int RBRACKET        = 0x5d;
+  static const int CHAR_a          = 0x61;
+  static const int CHAR_b          = 0x62;
+  static const int CHAR_e          = 0x65;
+  static const int CHAR_f          = 0x66;
+  static const int CHAR_l          = 0x6c;
+  static const int CHAR_n          = 0x6e;
+  static const int CHAR_r          = 0x72;
+  static const int CHAR_s          = 0x73;
+  static const int CHAR_t          = 0x74;
+  static const int CHAR_u          = 0x75;
+  static const int LBRACE          = 0x7b;
+  static const int RBRACE          = 0x7d;
+
+  final String source;
+  final JsonListener listener;
+  JsonParser(this.source, this.listener);
+
+  /** Parses [source], or throws if it fails. */
+  void parse() {
+    final List<int> states = <int>[];
+    int state = STATE_INITIAL;
+    int position = 0;
+    int length = source.length;
+    while (position < length) {
+      int char = source.codeUnitAt(position);
+      switch (char) {
+        case SPACE:
+        case CARRIAGE_RETURN:
+        case NEWLINE:
+        case TAB:
+          position++;
+          break;
+        case QUOTE:
+          if ((state & ALLOW_STRING_MASK) != 0) fail(position);
+          position = parseString(position + 1);
+          state |= VALUE_READ_BITS;
+          break;
+        case LBRACKET:
+          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
+          listener.beginArray();
+          states.add(state);
+          state = STATE_ARRAY_EMPTY;
+          position++;
+          break;
+        case LBRACE:
+          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
+          listener.beginObject();
+          states.add(state);
+          state = STATE_OBJECT_EMPTY;
+          position++;
+          break;
+        case CHAR_n:
+          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
+          position = parseNull(position);
+          state |= VALUE_READ_BITS;
+          break;
+        case CHAR_f:
+          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
+          position = parseFalse(position);
+          state |= VALUE_READ_BITS;
+          break;
+        case CHAR_t:
+          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
+          position = parseTrue(position);
+          state |= VALUE_READ_BITS;
+          break;
+        case COLON:
+          if (state != STATE_OBJECT_KEY) fail(position);
+          listener.propertyName();
+          state = STATE_OBJECT_COLON;
+          position++;
+          break;
+        case COMMA:
+          if (state == STATE_OBJECT_VALUE) {
+            listener.propertyValue();
+            state = STATE_OBJECT_COMMA;
+            position++;
+          } else if (state == STATE_ARRAY_VALUE) {
+            listener.arrayElement();
+            state = STATE_ARRAY_COMMA;
+            position++;
+          } else {
+            fail(position);
+          }
+          break;
+        case RBRACKET:
+          if (state == STATE_ARRAY_EMPTY) {
+            listener.endArray();
+          } else if (state == STATE_ARRAY_VALUE) {
+            listener.arrayElement();
+            listener.endArray();
+          } else {
+            fail(position);
+          }
+          state = states.removeLast() | VALUE_READ_BITS;
+          position++;
+          break;
+        case RBRACE:
+          if (state == STATE_OBJECT_EMPTY) {
+            listener.endObject();
+          } else if (state == STATE_OBJECT_VALUE) {
+            listener.propertyValue();
+            listener.endObject();
+          } else {
+            fail(position);
+          }
+          state = states.removeLast() | VALUE_READ_BITS;
+          position++;
+          break;
+        default:
+          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
+          position = parseNumber(char, position);
+          state |= VALUE_READ_BITS;
+          break;
+      }
+    }
+    if (state != STATE_END) fail(position);
+  }
+
+  /**
+   * Parses a "true" literal starting at [position].
+   *
+   * [:source[position]:] must be "t".
+   */
+  int parseTrue(int position) {
+    assert(source.codeUnitAt(position) == CHAR_t);
+    if (source.length < position + 4) fail(position, "Unexpected identifier");
+    if (source.codeUnitAt(position + 1) != CHAR_r ||
+        source.codeUnitAt(position + 2) != CHAR_u ||
+        source.codeUnitAt(position + 3) != CHAR_e) {
+      fail(position);
+    }
+    listener.handleBool(true);
+    return position + 4;
+  }
+
+  /**
+   * Parses a "false" literal starting at [position].
+   *
+   * [:source[position]:] must be "f".
+   */
+  int parseFalse(int position) {
+    assert(source.codeUnitAt(position) == CHAR_f);
+    if (source.length < position + 5) fail(position, "Unexpected identifier");
+    if (source.codeUnitAt(position + 1) != CHAR_a ||
+        source.codeUnitAt(position + 2) != CHAR_l ||
+        source.codeUnitAt(position + 3) != CHAR_s ||
+        source.codeUnitAt(position + 4) != CHAR_e) {
+      fail(position);
+    }
+    listener.handleBool(false);
+    return position + 5;
+  }
+
+  /** Parses a "null" literal starting at [position].
+   *
+   * [:source[position]:] must be "n".
+   */
+  int parseNull(int position) {
+    assert(source.codeUnitAt(position) == CHAR_n);
+    if (source.length < position + 4) fail(position, "Unexpected identifier");
+    if (source.codeUnitAt(position + 1) != CHAR_u ||
+        source.codeUnitAt(position + 2) != CHAR_l ||
+        source.codeUnitAt(position + 3) != CHAR_l) {
+      fail(position);
+    }
+    listener.handleNull();
+    return position + 4;
+  }
+
+  int parseString(int position) {
+    // Format: '"'([^\x00-\x1f\\\"]|'\\'[bfnrt/\\"])*'"'
+    // Initial position is right after first '"'.
+    int start = position;
+    int char;
+    do {
+      if (position == source.length) {
+        fail(start - 1, "Unterminated string");
+      }
+      char = source.codeUnitAt(position);
+      if (char == QUOTE) {
+        listener.handleString(source.substring(start, position));
+        return position + 1;
+      }
+      if (char < SPACE) {
+        fail(position, "Control character in string");
+      }
+      position++;
+    } while (char != BACKSLASH);
+    // Backslash escape detected. Collect character codes for rest of string.
+    int firstEscape = position - 1;
+    List<int> chars = <int>[];
+    while (true) {
+      if (position == source.length) {
+        fail(start - 1, "Unterminated string");
+      }
+      char = source.codeUnitAt(position);
+      switch (char) {
+        case CHAR_b: char = BACKSPACE; break;
+        case CHAR_f: char = FORM_FEED; break;
+        case CHAR_n: char = NEWLINE; break;
+        case CHAR_r: char = CARRIAGE_RETURN; break;
+        case CHAR_t: char = TAB; break;
+        case SLASH:
+        case BACKSLASH:
+        case QUOTE:
+          break;
+        case CHAR_u:
+          int hexStart = position - 1;
+          int value = 0;
+          for (int i = 0; i < 4; i++) {
+            position++;
+            if (position == source.length) {
+              fail(start - 1, "Unterminated string");
+            }
+            char = source.codeUnitAt(position);
+            char -= 0x30;
+            if (char < 0) fail(hexStart, "Invalid unicode escape");
+            if (char < 10) {
+              value = value * 16 + char;
+            } else {
+              char = (char | 0x20) - 0x31;
+              if (char < 0 || char > 5) {
+                fail(hexStart, "Invalid unicode escape");
+              }
+              value = value * 16 + char + 10;
+            }
+          }
+          char = value;
+          break;
+        default:
+          if (char < SPACE) fail(position, "Control character in string");
+          fail(position, "Unrecognized string escape");
+      }
+      do {
+        chars.add(char);
+        position++;
+        if (position == source.length) fail(start - 1, "Unterminated string");
+        char = source.codeUnitAt(position);
+        if (char == QUOTE) {
+          String result = new String.fromCharCodes(chars);
+          if (start < firstEscape) {
+            result = "${source.substring(start, firstEscape)}$result";
+          }
+          listener.handleString(result);
+          return position + 1;
+        }
+        if (char < SPACE) {
+          fail(position, "Control character in string");
+        }
+      } while (char != BACKSLASH);
+      position++;
+    }
+  }
+
+  int _handleLiteral(start, position, isDouble) {
+    String literal = source.substring(start, position);
+    // This correctly creates -0 for doubles.
+    num value = (isDouble ? double.parse(literal) : int.parse(literal));
+    listener.handleNumber(value);
+    return position;
+  }
+
+  int parseNumber(int char, int position) {
+    // Format:
+    //  '-'?('0'|[1-9][0-9]*)('.'[0-9]+)?([eE][+-]?[0-9]+)?
+    int start = position;
+    int length = source.length;
+    bool isDouble = false;
+    if (char == MINUS) {
+      position++;
+      if (position == length) fail(position, "Missing expected digit");
+      char = source.codeUnitAt(position);
+    }
+    if (char < CHAR_0 || char > CHAR_9) {
+      fail(position, "Missing expected digit");
+    }
+    if (char == CHAR_0) {
+      position++;
+      if (position == length) return _handleLiteral(start, position, false);
+      char = source.codeUnitAt(position);
+      if (CHAR_0 <= char && char <= CHAR_9) {
+        fail(position);
+      }
+    } else {
+      do {
+        position++;
+        if (position == length) return _handleLiteral(start, position, false);
+        char = source.codeUnitAt(position);
+      } while (CHAR_0 <= char && char <= CHAR_9);
+    }
+    if (char == DECIMALPOINT) {
+      isDouble = true;
+      position++;
+      if (position == length) fail(position, "Missing expected digit");
+      char = source.codeUnitAt(position);
+      if (char < CHAR_0 || char > CHAR_9) fail(position);
+      do {
+        position++;
+        if (position == length) return _handleLiteral(start, position, true);
+        char = source.codeUnitAt(position);
+      } while (CHAR_0 <= char && char <= CHAR_9);
+    }
+    if (char == CHAR_e || char == CHAR_E) {
+      isDouble = true;
+      position++;
+      if (position == length) fail(position, "Missing expected digit");
+      char = source.codeUnitAt(position);
+      if (char == PLUS || char == MINUS) {
+        position++;
+        if (position == length) fail(position, "Missing expected digit");
+        char = source.codeUnitAt(position);
+      }
+      if (char < CHAR_0 || char > CHAR_9) {
+        fail(position, "Missing expected digit");
+      }
+      do {
+        position++;
+        if (position == length) return _handleLiteral(start, position, true);
+        char = source.codeUnitAt(position);
+      } while (CHAR_0 <= char && char <= CHAR_9);
+    }
+    return _handleLiteral(start, position, isDouble);
+  }
+
+  void fail(int position, [String message]) {
+    if (message == null) message = "Unexpected character";
+    listener.fail(source, position, message);
+    // If the listener didn't throw, do it here.
+    String slice;
+    int sliceEnd = position + 20;
+    if (sliceEnd > source.length) {
+      slice = "'${source.substring(position)}'";
+    } else {
+      slice = "'${source.substring(position, sliceEnd)}...'";
+    }
+    throw new FormatException("Unexpected character at $position: $slice");
+  }
+}
+
+
+class _JsonStringifier {
+  StringBuffer sb;
+  List<Object> seen;  // TODO: that should be identity set.
+
+  _JsonStringifier(this.sb) : seen = [];
+
+  static String stringify(final object) {
+    StringBuffer output = new StringBuffer();
+    _JsonStringifier stringifier = new _JsonStringifier(output);
+    stringifier.stringifyValue(object);
+    return output.toString();
+  }
+
+  static void printOn(final object, StringBuffer output) {
+    _JsonStringifier stringifier = new _JsonStringifier(output);
+    stringifier.stringifyValue(object);
+  }
+
+  static String numberToString(num x) {
+    return x.toString();
+  }
+
+  // ('0' + x) or ('a' + x - 10)
+  static int hexDigit(int x) => x < 10 ? 48 + x : 87 + x;
+
+  static void escape(StringBuffer sb, String s) {
+    final int length = s.length;
+    bool needsEscape = false;
+    final charCodes = new List<int>();
+    for (int i = 0; i < length; i++) {
+      int charCode = s.codeUnitAt(i);
+      if (charCode < 32) {
+        needsEscape = true;
+        charCodes.add(JsonParser.BACKSLASH);
+        switch (charCode) {
+        case JsonParser.BACKSPACE:
+          charCodes.add(JsonParser.CHAR_b);
+          break;
+        case JsonParser.TAB:
+          charCodes.add(JsonParser.CHAR_t);
+          break;
+        case JsonParser.NEWLINE:
+          charCodes.add(JsonParser.CHAR_n);
+          break;
+        case JsonParser.FORM_FEED:
+          charCodes.add(JsonParser.CHAR_f);
+          break;
+        case JsonParser.CARRIAGE_RETURN:
+          charCodes.add(JsonParser.CHAR_r);
+          break;
+        default:
+          charCodes.add(JsonParser.CHAR_u);
+          charCodes.add(hexDigit((charCode >> 12) & 0xf));
+          charCodes.add(hexDigit((charCode >> 8) & 0xf));
+          charCodes.add(hexDigit((charCode >> 4) & 0xf));
+          charCodes.add(hexDigit(charCode & 0xf));
+          break;
+        }
+      } else if (charCode == JsonParser.QUOTE ||
+          charCode == JsonParser.BACKSLASH) {
+        needsEscape = true;
+        charCodes.add(JsonParser.BACKSLASH);
+        charCodes.add(charCode);
+      } else {
+        charCodes.add(charCode);
+      }
+    }
+    sb.write(needsEscape ? new String.fromCharCodes(charCodes) : s);
+  }
+
+  void checkCycle(final object) {
+    // TODO: use Iterables.
+    for (int i = 0; i < seen.length; i++) {
+      if (identical(seen[i], object)) {
+        throw 'Cyclic structure';
+      }
+    }
+    seen.add(object);
+  }
+
+  void stringifyValue(final object) {
+    // Tries stringifying object directly. If it's not a simple value, List or
+    // Map, call toJson() to get a custom representation and try serializing
+    // that.
+    if (!stringifyJsonValue(object)) {
+      checkCycle(object);
+      try {
+        var customJson = object.toJson();
+        if (!stringifyJsonValue(customJson)) {
+          throw new JsonUnsupportedObjectError(object);
+        }
+        seen.removeLast();
+      } catch (e) {
+        throw new JsonUnsupportedObjectError.withCause(object, e);
+      }
+    }
+  }
+
+  /**
+   * Serializes a [num], [String], [bool], [Null], [List] or [Map] value.
+   *
+   * Returns true if the value is one of these types, and false if not.
+   * If a value is both a [List] and a [Map], it's serialized as a [List].
+   */
+  bool stringifyJsonValue(final object) {
+    if (object is num) {
+      // TODO: use writeOn.
+      sb.write(numberToString(object));
+      return true;
+    } else if (identical(object, true)) {
+      sb.write('true');
+      return true;
+    } else if (identical(object, false)) {
+      sb.write('false');
+       return true;
+    } else if (object == null) {
+      sb.write('null');
+      return true;
+    } else if (object is String) {
+      sb.write('"');
+      escape(sb, object);
+      sb.write('"');
+      return true;
+    } else if (object is List) {
+      checkCycle(object);
+      List a = object;
+      sb.write('[');
+      if (a.length > 0) {
+        stringifyValue(a[0]);
+        // TODO: switch to Iterables.
+        for (int i = 1; i < a.length; i++) {
+          sb.write(',');
+          stringifyValue(a[i]);
+        }
+      }
+      sb.write(']');
+      seen.removeLast();
+      return true;
+    } else if (object is Map) {
+      checkCycle(object);
+      Map<String, Object> m = object;
+      sb.write('{');
+      bool first = true;
+      m.forEach((String key, Object value) {
+        if (!first) {
+          sb.write(',"');
+        } else {
+          sb.write('"');
+        }
+        escape(sb, key);
+        sb.write('":');
+        stringifyValue(value);
+        first = false;
+      });
+      sb.write('}');
+      seen.removeLast();
+      return true;
+    } else {
+      return false;
+    }
+  }
+}
diff --git a/sdk/lib/json/json_base.dart b/sdk/lib/json/json_base.dart
deleted file mode 100644
index 8faa30e..0000000
--- a/sdk/lib/json/json_base.dart
+++ /dev/null
@@ -1,807 +0,0 @@
-// Copyright (c) 2012, 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 dart.json;
-
-// JSON parsing and serialization.
-
-/**
- * Error thrown by JSON serialization if an object cannot be serialized.
- *
- * The [unsupportedObject] field holds that object that failed to be serialized.
- *
- * If an object isn't directly serializable, the serializer calls the 'toJson'
- * method on the object. If that call fails, the error will be stored in the
- * [cause] field. If the call returns an object that isn't directly
- * serializable, the [cause] will be null.
- */
-class JsonUnsupportedObjectError implements Error {
-  /** The object that could not be serialized. */
-  final unsupportedObject;
-  /** The exception thrown by object's [:toJson:] method, if any. */
-  final cause;
-  JsonUnsupportedObjectError(this.unsupportedObject) : cause = null;
-  JsonUnsupportedObjectError.withCause(this.unsupportedObject, this.cause);
-
-  String toString() {
-    if (cause != null) {
-      return "Calling toJson method on object failed.";
-    } else {
-      return "Object toJson method returns non-serializable value.";
-    }
-  }
-}
-
-
-/**
- * Parses [json] and build the corresponding parsed JSON value.
- *
- * Parsed JSON values are of the types [num], [String], [bool], [Null],
- * [List]s of parsed JSON values or [Map]s from [String] to parsed
- * JSON values.
- *
- * The optional [revivier] function, if provided, is called once for each
- * object or list property parsed. The arguments are the property name
- * ([String]) or list index ([int]), and the value is the parsed value.
- * The return value of the revivier will be used as the value of that property
- * instead the parsed value.
- *
- * Throws [FormatException] if the input is not valid JSON text.
- */
-external parse(String json, [reviver(var key, var value)]);
-
-_parse(String json, reviver(var key, var value)) {
-  BuildJsonListener listener;
-  if (reviver == null) {
-    listener = new BuildJsonListener();
-  } else {
-    listener = new ReviverJsonListener(reviver);
-  }
-  new JsonParser(json, listener).parse();
-  return listener.result;
-}
-
-/**
- * Serializes [object] into a JSON string.
- *
- * Directly serializable types are [num], [String], [bool], [Null], [List]
- * and [Map].
- * For [List], the elements must all be serializable.
- * For [Map], the keys must be [String] and the values must be serializable.
- * If a value is any other type is attempted serialized, a "toJson()" method
- * is invoked on the object and the result, which must be a directly
- * serializable type, is serialized instead of the original value.
- * If the object does not support this method, throws, or returns a
- * value that is not directly serializable, a [JsonUnsupportedObjectError]
- * exception is thrown. If the call throws (including the case where there
- * is no nullary "toJson" method, the error is caught and stored in the
- * [JsonUnsupportedObjectError]'s [:cause:] field.
- *Json
- * Objects should not change during serialization.
- * If an object is serialized more than once, [stringify] is allowed to cache
- * the JSON text for it. I.e., if an object changes after it is first
- * serialized, the new values may or may not be reflected in the result.
- */
-String stringify(Object object) {
-  return _JsonStringifier.stringify(object);
-}
-
-/**
- * Serializes [object] into [output] stream.
- *
- * Performs the same operations as [stringify] but outputs the resulting
- * string to an existing [StringBuffer] instead of creating a new [String].
- *
- * If serialization fails by throwing, some data might have been added to
- * [output], but it won't contain valid JSON text.
- */
-void printOn(Object object, StringBuffer output) {
-  return _JsonStringifier.printOn(object, output);
-}
-
-//// Implementation ///////////////////////////////////////////////////////////
-
-// Simple API for JSON parsing.
-
-abstract class JsonListener {
-  void handleString(String value) {}
-  void handleNumber(num value) {}
-  void handleBool(bool value) {}
-  void handleNull() {}
-  void beginObject() {}
-  void propertyName() {}
-  void propertyValue() {}
-  void endObject() {}
-  void beginArray() {}
-  void arrayElement() {}
-  void endArray() {}
-  /** Called on failure to parse [source]. */
-  void fail(String source, int position, String message) {}
-}
-
-/**
- * A [JsonListener] that builds data objects from the parser events.
- *
- * This is a simple stack-based object builder. It keeps the most recently
- * seen value in a variable, and uses it depending on the following event.
- */
-class BuildJsonListener extends JsonListener {
-  /**
-   * Stack used to handle nested containers.
-   *
-   * The current container is pushed on the stack when a new one is
-   * started. If the container is a [Map], there is also a current [key]
-   * which is also stored on the stack.
-   */
-  List stack = [];
-  /** The current [Map] or [List] being built. */
-  var currentContainer;
-  /** The most recently read property key. */
-  String key;
-  /** The most recently read value. */
-  var value;
-
-  /** Pushes the currently active container (and key, if a [Map]). */
-  void pushContainer() {
-    if (currentContainer is Map) stack.add(key);
-    stack.add(currentContainer);
-  }
-
-  /** Pops the top container from the [stack], including a key if applicable. */
-  void popContainer() {
-    value = currentContainer;
-    currentContainer = stack.removeLast();
-    if (currentContainer is Map) key = stack.removeLast();
-  }
-
-  void handleString(String value) { this.value = value; }
-  void handleNumber(num value) { this.value = value; }
-  void handleBool(bool value) { this.value = value; }
-  void handleNull() { this.value = value; }
-
-  void beginObject() {
-    pushContainer();
-    currentContainer = {};
-  }
-
-  void propertyName() {
-    key = value;
-    value = null;
-  }
-
-  void propertyValue() {
-    Map map = currentContainer;
-    map[key] = value;
-    key = value = null;
-  }
-
-  void endObject() {
-    popContainer();
-  }
-
-  void beginArray() {
-    pushContainer();
-    currentContainer = [];
-  }
-
-  void arrayElement() {
-    List list = currentContainer;
-    currentContainer.add(value);
-    value = null;
-  }
-
-  void endArray() {
-    popContainer();
-  }
-
-  /** Read out the final result of parsing a JSON string. */
-  get result {
-    assert(currentContainer == null);
-    return value;
-  }
-}
-
-typedef _Reviver(var key, var value);
-
-class ReviverJsonListener extends BuildJsonListener {
-  final _Reviver reviver;
-  ReviverJsonListener(reviver(key, value)) : this.reviver = reviver;
-
-  void arrayElement() {
-    List list = currentContainer;
-    value = reviver(list.length, value);
-    super.arrayElement();
-  }
-
-  void propertyValue() {
-    value = reviver(key, value);
-    super.propertyValue();
-  }
-
-  get result {
-    return reviver("", value);
-  }
-}
-
-class JsonParser {
-  // A simple non-recursive state-based parser for JSON.
-  //
-  // Literal values accepted in states ARRAY_EMPTY, ARRAY_COMMA, OBJECT_COLON
-  // and strings also in OBJECT_EMPTY, OBJECT_COMMA.
-  //               VALUE  STRING  :  ,  }  ]        Transitions to
-  // EMPTY            X      X                   -> END
-  // ARRAY_EMPTY      X      X             @     -> ARRAY_VALUE / pop
-  // ARRAY_VALUE                     @     @     -> ARRAY_COMMA / pop
-  // ARRAY_COMMA      X      X                   -> ARRAY_VALUE
-  // OBJECT_EMPTY            X          @        -> OBJECT_KEY / pop
-  // OBJECT_KEY                   @              -> OBJECT_COLON
-  // OBJECT_COLON     X      X                   -> OBJECT_VALUE
-  // OBJECT_VALUE                    @  @        -> OBJECT_COMMA / pop
-  // OBJECT_COMMA            X                   -> OBJECT_KEY
-  // END
-  // Starting a new array or object will push the current state. The "pop"
-  // above means restoring this state and then marking it as an ended value.
-  // X means generic handling, @ means special handling for just that
-  // state - that is, values are handled generically, only punctuation
-  // cares about the current state.
-  // Values for states are chosen so bits 0 and 1 tell whether
-  // a string/value is allowed, and setting bits 0 through 2 after a value
-  // gets to the next state (not empty, doesn't allow a value).
-
-  // State building-block constants.
-  static const int INSIDE_ARRAY = 1;
-  static const int INSIDE_OBJECT = 2;
-  static const int AFTER_COLON = 3;  // Always inside object.
-
-  static const int ALLOW_STRING_MASK = 8;  // Allowed if zero.
-  static const int ALLOW_VALUE_MASK = 4;  // Allowed if zero.
-  static const int ALLOW_VALUE = 0;
-  static const int STRING_ONLY = 4;
-  static const int NO_VALUES = 12;
-
-  // Objects and arrays are "empty" until their first property/element.
-  static const int EMPTY = 0;
-  static const int NON_EMPTY = 16;
-  static const int EMPTY_MASK = 16;  // Empty if zero.
-
-
-  static const int VALUE_READ_BITS = NO_VALUES | NON_EMPTY;
-
-  // Actual states.
-  static const int STATE_INITIAL      = EMPTY | ALLOW_VALUE;
-  static const int STATE_END          = NON_EMPTY | NO_VALUES;
-
-  static const int STATE_ARRAY_EMPTY  = INSIDE_ARRAY | EMPTY | ALLOW_VALUE;
-  static const int STATE_ARRAY_VALUE  = INSIDE_ARRAY | NON_EMPTY | NO_VALUES;
-  static const int STATE_ARRAY_COMMA  = INSIDE_ARRAY | NON_EMPTY | ALLOW_VALUE;
-
-  static const int STATE_OBJECT_EMPTY = INSIDE_OBJECT | EMPTY | STRING_ONLY;
-  static const int STATE_OBJECT_KEY   = INSIDE_OBJECT | NON_EMPTY | NO_VALUES;
-  static const int STATE_OBJECT_COLON = AFTER_COLON | NON_EMPTY | ALLOW_VALUE;
-  static const int STATE_OBJECT_VALUE = AFTER_COLON | NON_EMPTY | NO_VALUES;
-  static const int STATE_OBJECT_COMMA = INSIDE_OBJECT | NON_EMPTY | STRING_ONLY;
-
-  // Character code constants.
-  static const int BACKSPACE       = 0x08;
-  static const int TAB             = 0x09;
-  static const int NEWLINE         = 0x0a;
-  static const int CARRIAGE_RETURN = 0x0d;
-  static const int FORM_FEED       = 0x0c;
-  static const int SPACE           = 0x20;
-  static const int QUOTE           = 0x22;
-  static const int PLUS            = 0x2b;
-  static const int COMMA           = 0x2c;
-  static const int MINUS           = 0x2d;
-  static const int DECIMALPOINT    = 0x2e;
-  static const int SLASH           = 0x2f;
-  static const int CHAR_0          = 0x30;
-  static const int CHAR_9          = 0x39;
-  static const int COLON           = 0x3a;
-  static const int CHAR_E          = 0x45;
-  static const int LBRACKET        = 0x5b;
-  static const int BACKSLASH       = 0x5c;
-  static const int RBRACKET        = 0x5d;
-  static const int CHAR_a          = 0x61;
-  static const int CHAR_b          = 0x62;
-  static const int CHAR_e          = 0x65;
-  static const int CHAR_f          = 0x66;
-  static const int CHAR_l          = 0x6c;
-  static const int CHAR_n          = 0x6e;
-  static const int CHAR_r          = 0x72;
-  static const int CHAR_s          = 0x73;
-  static const int CHAR_t          = 0x74;
-  static const int CHAR_u          = 0x75;
-  static const int LBRACE          = 0x7b;
-  static const int RBRACE          = 0x7d;
-
-  final String source;
-  final JsonListener listener;
-  JsonParser(this.source, this.listener);
-
-  /** Parses [source], or throws if it fails. */
-  void parse() {
-    final List<int> states = <int>[];
-    int state = STATE_INITIAL;
-    int position = 0;
-    int length = source.length;
-    while (position < length) {
-      int char = source.codeUnitAt(position);
-      switch (char) {
-        case SPACE:
-        case CARRIAGE_RETURN:
-        case NEWLINE:
-        case TAB:
-          position++;
-          break;
-        case QUOTE:
-          if ((state & ALLOW_STRING_MASK) != 0) fail(position);
-          position = parseString(position + 1);
-          state |= VALUE_READ_BITS;
-          break;
-        case LBRACKET:
-          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
-          listener.beginArray();
-          states.add(state);
-          state = STATE_ARRAY_EMPTY;
-          position++;
-          break;
-        case LBRACE:
-          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
-          listener.beginObject();
-          states.add(state);
-          state = STATE_OBJECT_EMPTY;
-          position++;
-          break;
-        case CHAR_n:
-          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
-          position = parseNull(position);
-          state |= VALUE_READ_BITS;
-          break;
-        case CHAR_f:
-          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
-          position = parseFalse(position);
-          state |= VALUE_READ_BITS;
-          break;
-        case CHAR_t:
-          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
-          position = parseTrue(position);
-          state |= VALUE_READ_BITS;
-          break;
-        case COLON:
-          if (state != STATE_OBJECT_KEY) fail(position);
-          listener.propertyName();
-          state = STATE_OBJECT_COLON;
-          position++;
-          break;
-        case COMMA:
-          if (state == STATE_OBJECT_VALUE) {
-            listener.propertyValue();
-            state = STATE_OBJECT_COMMA;
-            position++;
-          } else if (state == STATE_ARRAY_VALUE) {
-            listener.arrayElement();
-            state = STATE_ARRAY_COMMA;
-            position++;
-          } else {
-            fail(position);
-          }
-          break;
-        case RBRACKET:
-          if (state == STATE_ARRAY_EMPTY) {
-            listener.endArray();
-          } else if (state == STATE_ARRAY_VALUE) {
-            listener.arrayElement();
-            listener.endArray();
-          } else {
-            fail(position);
-          }
-          state = states.removeLast() | VALUE_READ_BITS;
-          position++;
-          break;
-        case RBRACE:
-          if (state == STATE_OBJECT_EMPTY) {
-            listener.endObject();
-          } else if (state == STATE_OBJECT_VALUE) {
-            listener.propertyValue();
-            listener.endObject();
-          } else {
-            fail(position);
-          }
-          state = states.removeLast() | VALUE_READ_BITS;
-          position++;
-          break;
-        default:
-          if ((state & ALLOW_VALUE_MASK) != 0) fail(position);
-          position = parseNumber(char, position);
-          state |= VALUE_READ_BITS;
-          break;
-      }
-    }
-    if (state != STATE_END) fail(position);
-  }
-
-  /**
-   * Parses a "true" literal starting at [position].
-   *
-   * [:source[position]:] must be "t".
-   */
-  int parseTrue(int position) {
-    assert(source.codeUnitAt(position) == CHAR_t);
-    if (source.length < position + 4) fail(position, "Unexpected identifier");
-    if (source.codeUnitAt(position + 1) != CHAR_r ||
-        source.codeUnitAt(position + 2) != CHAR_u ||
-        source.codeUnitAt(position + 3) != CHAR_e) {
-      fail(position);
-    }
-    listener.handleBool(true);
-    return position + 4;
-  }
-
-  /**
-   * Parses a "false" literal starting at [position].
-   *
-   * [:source[position]:] must be "f".
-   */
-  int parseFalse(int position) {
-    assert(source.codeUnitAt(position) == CHAR_f);
-    if (source.length < position + 5) fail(position, "Unexpected identifier");
-    if (source.codeUnitAt(position + 1) != CHAR_a ||
-        source.codeUnitAt(position + 2) != CHAR_l ||
-        source.codeUnitAt(position + 3) != CHAR_s ||
-        source.codeUnitAt(position + 4) != CHAR_e) {
-      fail(position);
-    }
-    listener.handleBool(false);
-    return position + 5;
-  }
-
-  /** Parses a "null" literal starting at [position].
-   *
-   * [:source[position]:] must be "n".
-   */
-  int parseNull(int position) {
-    assert(source.codeUnitAt(position) == CHAR_n);
-    if (source.length < position + 4) fail(position, "Unexpected identifier");
-    if (source.codeUnitAt(position + 1) != CHAR_u ||
-        source.codeUnitAt(position + 2) != CHAR_l ||
-        source.codeUnitAt(position + 3) != CHAR_l) {
-      fail(position);
-    }
-    listener.handleNull();
-    return position + 4;
-  }
-
-  int parseString(int position) {
-    // Format: '"'([^\x00-\x1f\\\"]|'\\'[bfnrt/\\"])*'"'
-    // Initial position is right after first '"'.
-    int start = position;
-    int char;
-    do {
-      if (position == source.length) {
-        fail(start - 1, "Unterminated string");
-      }
-      char = source.codeUnitAt(position);
-      if (char == QUOTE) {
-        listener.handleString(source.substring(start, position));
-        return position + 1;
-      }
-      if (char < SPACE) {
-        fail(position, "Control character in string");
-      }
-      position++;
-    } while (char != BACKSLASH);
-    // Backslash escape detected. Collect character codes for rest of string.
-    int firstEscape = position - 1;
-    List<int> chars = <int>[];
-    while (true) {
-      if (position == source.length) {
-        fail(start - 1, "Unterminated string");
-      }
-      char = source.codeUnitAt(position);
-      switch (char) {
-        case CHAR_b: char = BACKSPACE; break;
-        case CHAR_f: char = FORM_FEED; break;
-        case CHAR_n: char = NEWLINE; break;
-        case CHAR_r: char = CARRIAGE_RETURN; break;
-        case CHAR_t: char = TAB; break;
-        case SLASH:
-        case BACKSLASH:
-        case QUOTE:
-          break;
-        case CHAR_u:
-          int hexStart = position - 1;
-          int value = 0;
-          for (int i = 0; i < 4; i++) {
-            position++;
-            if (position == source.length) {
-              fail(start - 1, "Unterminated string");
-            }
-            char = source.codeUnitAt(position);
-            char -= 0x30;
-            if (char < 0) fail(hexStart, "Invalid unicode escape");
-            if (char < 10) {
-              value = value * 16 + char;
-            } else {
-              char = (char | 0x20) - 0x31;
-              if (char < 0 || char > 5) {
-                fail(hexStart, "Invalid unicode escape");
-              }
-              value = value * 16 + char + 10;
-            }
-          }
-          char = value;
-          break;
-        default:
-          if (char < SPACE) fail(position, "Control character in string");
-          fail(position, "Unrecognized string escape");
-      }
-      do {
-        chars.add(char);
-        position++;
-        if (position == source.length) fail(start - 1, "Unterminated string");
-        char = source.codeUnitAt(position);
-        if (char == QUOTE) {
-          String result = new String.fromCharCodes(chars);
-          if (start < firstEscape) {
-            result = "${source.substring(start, firstEscape)}$result";
-          }
-          listener.handleString(result);
-          return position + 1;
-        }
-        if (char < SPACE) {
-          fail(position, "Control character in string");
-        }
-      } while (char != BACKSLASH);
-      position++;
-    }
-  }
-
-  int _handleLiteral(start, position, isDouble) {
-    String literal = source.substring(start, position);
-    // This correctly creates -0 for doubles.
-    num value = (isDouble ? double.parse(literal) : int.parse(literal));
-    listener.handleNumber(value);
-    return position;
-  }
-
-  int parseNumber(int char, int position) {
-    // Format:
-    //  '-'?('0'|[1-9][0-9]*)('.'[0-9]+)?([eE][+-]?[0-9]+)?
-    int start = position;
-    int length = source.length;
-    bool isDouble = false;
-    if (char == MINUS) {
-      position++;
-      if (position == length) fail(position, "Missing expected digit");
-      char = source.codeUnitAt(position);
-    }
-    if (char < CHAR_0 || char > CHAR_9) {
-      fail(position, "Missing expected digit");
-    }
-    if (char == CHAR_0) {
-      position++;
-      if (position == length) return _handleLiteral(start, position, false);
-      char = source.codeUnitAt(position);
-      if (CHAR_0 <= char && char <= CHAR_9) {
-        fail(position);
-      }
-    } else {
-      do {
-        position++;
-        if (position == length) return _handleLiteral(start, position, false);
-        char = source.codeUnitAt(position);
-      } while (CHAR_0 <= char && char <= CHAR_9);
-    }
-    if (char == DECIMALPOINT) {
-      isDouble = true;
-      position++;
-      if (position == length) fail(position, "Missing expected digit");
-      char = source.codeUnitAt(position);
-      if (char < CHAR_0 || char > CHAR_9) fail(position);
-      do {
-        position++;
-        if (position == length) return _handleLiteral(start, position, true);
-        char = source.codeUnitAt(position);
-      } while (CHAR_0 <= char && char <= CHAR_9);
-    }
-    if (char == CHAR_e || char == CHAR_E) {
-      isDouble = true;
-      position++;
-      if (position == length) fail(position, "Missing expected digit");
-      char = source.codeUnitAt(position);
-      if (char == PLUS || char == MINUS) {
-        position++;
-        if (position == length) fail(position, "Missing expected digit");
-        char = source.codeUnitAt(position);
-      }
-      if (char < CHAR_0 || char > CHAR_9) {
-        fail(position, "Missing expected digit");
-      }
-      do {
-        position++;
-        if (position == length) return _handleLiteral(start, position, true);
-        char = source.codeUnitAt(position);
-      } while (CHAR_0 <= char && char <= CHAR_9);
-    }
-    return _handleLiteral(start, position, isDouble);
-  }
-
-  void fail(int position, [String message]) {
-    if (message == null) message = "Unexpected character";
-    listener.fail(source, position, message);
-    // If the listener didn't throw, do it here.
-    String slice;
-    int sliceEnd = position + 20;
-    if (sliceEnd > source.length) {
-      slice = "'${source.substring(position)}'";
-    } else {
-      slice = "'${source.substring(position, sliceEnd)}...'";
-    }
-    throw new FormatException("Unexpected character at $position: $slice");
-  }
-}
-
-
-class _JsonStringifier {
-  StringBuffer sb;
-  List<Object> seen;  // TODO: that should be identity set.
-
-  _JsonStringifier(this.sb) : seen = [];
-
-  static String stringify(final object) {
-    StringBuffer output = new StringBuffer();
-    _JsonStringifier stringifier = new _JsonStringifier(output);
-    stringifier.stringifyValue(object);
-    return output.toString();
-  }
-
-  static void printOn(final object, StringBuffer output) {
-    _JsonStringifier stringifier = new _JsonStringifier(output);
-    stringifier.stringifyValue(object);
-  }
-
-  static String numberToString(num x) {
-    return x.toString();
-  }
-
-  // ('0' + x) or ('a' + x - 10)
-  static int hexDigit(int x) => x < 10 ? 48 + x : 87 + x;
-
-  static void escape(StringBuffer sb, String s) {
-    final int length = s.length;
-    bool needsEscape = false;
-    final charCodes = new List<int>();
-    for (int i = 0; i < length; i++) {
-      int charCode = s.codeUnitAt(i);
-      if (charCode < 32) {
-        needsEscape = true;
-        charCodes.add(JsonParser.BACKSLASH);
-        switch (charCode) {
-        case JsonParser.BACKSPACE:
-          charCodes.add(JsonParser.CHAR_b);
-          break;
-        case JsonParser.TAB:
-          charCodes.add(JsonParser.CHAR_t);
-          break;
-        case JsonParser.NEWLINE:
-          charCodes.add(JsonParser.CHAR_n);
-          break;
-        case JsonParser.FORM_FEED:
-          charCodes.add(JsonParser.CHAR_f);
-          break;
-        case JsonParser.CARRIAGE_RETURN:
-          charCodes.add(JsonParser.CHAR_r);
-          break;
-        default:
-          charCodes.add(JsonParser.CHAR_u);
-          charCodes.add(hexDigit((charCode >> 12) & 0xf));
-          charCodes.add(hexDigit((charCode >> 8) & 0xf));
-          charCodes.add(hexDigit((charCode >> 4) & 0xf));
-          charCodes.add(hexDigit(charCode & 0xf));
-          break;
-        }
-      } else if (charCode == JsonParser.QUOTE ||
-          charCode == JsonParser.BACKSLASH) {
-        needsEscape = true;
-        charCodes.add(JsonParser.BACKSLASH);
-        charCodes.add(charCode);
-      } else {
-        charCodes.add(charCode);
-      }
-    }
-    sb.write(needsEscape ? new String.fromCharCodes(charCodes) : s);
-  }
-
-  void checkCycle(final object) {
-    // TODO: use Iterables.
-    for (int i = 0; i < seen.length; i++) {
-      if (identical(seen[i], object)) {
-        throw 'Cyclic structure';
-      }
-    }
-    seen.add(object);
-  }
-
-  void stringifyValue(final object) {
-    // Tries stringifying object directly. If it's not a simple value, List or
-    // Map, call toJson() to get a custom representation and try serializing
-    // that.
-    if (!stringifyJsonValue(object)) {
-      checkCycle(object);
-      try {
-        var customJson = object.toJson();
-        if (!stringifyJsonValue(customJson)) {
-          throw new JsonUnsupportedObjectError(object);
-        }
-        seen.removeLast();
-      } catch (e) {
-        throw new JsonUnsupportedObjectError.withCause(object, e);
-      }
-    }
-  }
-
-  /**
-   * Serializes a [num], [String], [bool], [Null], [List] or [Map] value.
-   *
-   * Returns true if the value is one of these types, and false if not.
-   * If a value is both a [List] and a [Map], it's serialized as a [List].
-   */
-  bool stringifyJsonValue(final object) {
-    if (object is num) {
-      // TODO: use writeOn.
-      sb.write(numberToString(object));
-      return true;
-    } else if (identical(object, true)) {
-      sb.write('true');
-      return true;
-    } else if (identical(object, false)) {
-      sb.write('false');
-       return true;
-    } else if (object == null) {
-      sb.write('null');
-      return true;
-    } else if (object is String) {
-      sb.write('"');
-      escape(sb, object);
-      sb.write('"');
-      return true;
-    } else if (object is List) {
-      checkCycle(object);
-      List a = object;
-      sb.write('[');
-      if (a.length > 0) {
-        stringifyValue(a[0]);
-        // TODO: switch to Iterables.
-        for (int i = 1; i < a.length; i++) {
-          sb.write(',');
-          stringifyValue(a[i]);
-        }
-      }
-      sb.write(']');
-      seen.removeLast();
-      return true;
-    } else if (object is Map) {
-      checkCycle(object);
-      Map<String, Object> m = object;
-      sb.write('{');
-      bool first = true;
-      m.forEach((String key, Object value) {
-        if (!first) {
-          sb.write(',"');
-        } else {
-          sb.write('"');
-        }
-        escape(sb, key);
-        sb.write('":');
-        stringifyValue(value);
-        first = false;
-      });
-      sb.write('}');
-      seen.removeLast();
-      return true;
-    } else {
-      return false;
-    }
-  }
-}
diff --git a/sdk/lib/json/json_sources.gypi b/sdk/lib/json/json_sources.gypi
index 9311d82..407c5de 100644
--- a/sdk/lib/json/json_sources.gypi
+++ b/sdk/lib/json/json_sources.gypi
@@ -6,7 +6,6 @@
 {
   'sources': [
     'json.dart',
-    # The above file needs to be first as it lists the parts below.
-    'json_base.dart',
+    # The above file needs to be first if additional parts are added to the lib.
   ],
 }
diff --git a/sdk/lib/math/base.dart b/sdk/lib/math/base.dart
deleted file mode 100644
index e75286d..0000000
--- a/sdk/lib/math/base.dart
+++ /dev/null
@@ -1,221 +0,0 @@
-// Copyright (c) 2012, 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 dart.math;
-
-/**
- * Base of the natural logarithms.
- *
- * Typically written as "e".
- */
-const double E = 2.718281828459045;
-
-/**
- * Natural logarithm of 10.
- */
-const double LN10 =  2.302585092994046;
-
-/**
- * Natural logarithm of 2.
- */
-const double LN2 =  0.6931471805599453;
-
-/**
- * Base-2 logarithm of [E].
- */
-const double LOG2E = 1.4426950408889634;
-
-/**
- * Base-10 logarithm of [E].
- */
-const double LOG10E = 0.4342944819032518;
-
-/**
- * The PI constant.
- */
-const double PI = 3.1415926535897932;
-
-/**
- * Square root of 1/2.
- */
-const double SQRT1_2 = 0.7071067811865476;
-
-/**
- * Square root of 2.
- */
-const double SQRT2 = 1.4142135623730951;
-
-/**
-  * Returns the lesser of two numbers.
-  *
-  * Returns NaN if either argument is NaN.
-  * The lesser of [:-0.0:] and [:0.0:] is [:-0.0:].
-  * If the arguments are otherwise equal (including int and doubles with the
-  * same mathematical value) then it is unspecified which of the two arguments
-  * is returned.
-  */
-num min(num a, num b) {
-  if (a is num) {
-    // TODO(floitsch): merge this if into the previous one, once dart2js
-    // correctly propagates types for logical ands.
-    if (b is num) {
-      if (a > b) return b;
-      if (a < b) return a;
-      if (b is double) {
-        // Special case for NaN and -0.0. If one argument is NaN return NaN.
-        // [min] must also distinguish between -0.0 and 0.0.
-        if (a is double) {
-          if (a == 0.0) {
-            // a is either 0.0 or -0.0. b is either 0.0, -0.0 or NaN.
-            // The following returns -0.0 if either a or b is -0.0, and it
-            // returns NaN if b is NaN.
-            return (a + b) * a * b;
-          }
-        }
-        // Check for NaN and b == -0.0.
-        if (a == 0 && b.isNegative || b.isNaN) return b;
-        return a;
-      }
-      return a;
-    }
-    throw new ArgumentError(b);
-  }
-  throw new ArgumentError(a);
-}
-
-/**
-  * Returns the larger of two numbers.
-  *
-  * Returns NaN if either argument is NaN.
-  * The larger of [:-0.0:] and [:0.0:] is [:0.0:]. If the arguments are
-  * otherwise equal (including int and doubles with the same mathematical value)
-  * then it is unspecified which of the two arguments is returned.
-  */
-num max(num a, num b) {
-  if (a is num) {
-    // TODO(floitsch): merge this if into the previous one, once dart2js
-    // correctly propagates types for logical ands.
-    if (b is num) {
-      if (a > b) return a;
-      if (a < b) return b;
-      if (b is double) {
-        // Special case for NaN and -0.0. If one argument is NaN return NaN.
-        // [max] must also distinguish between -0.0 and 0.0.
-        if (a is double) {
-          if (a == 0.0) {
-            // a is either 0.0 or -0.0. b is either 0.0, -0.0, or NaN.
-            // The following returns 0.0 if either a or b is 0.0, and it
-            // returns NaN if b is NaN.
-            return a + b;
-          }
-        }
-        // Check for NaN.
-        if (b.isNaN) return b;
-        return a;
-      }
-      // max(-0.0, 0) must return 0.
-      if (b == 0 && a.isNegative) return b;
-      return a;
-    }
-    throw new ArgumentError(b);
-  }
-  throw new ArgumentError(a);
-}
-
-/**
- * A variant of [atan].
- *
- * Converts both arguments to doubles.
- *
- * Returns the angle between the positive x-axis and the vector ([b],[a]).
- * The result, in radians, is in the range -PI..PI.
- *
- * If [b] is positive, this is the same as [:atan(b/a):].
- *
- * The result is negative when [a] is negative (including when [a] is the
- * double -0.0).
- *
- * If [a] is equal to zero, the vector ([b],[a]) is considered parallel to
- * the x-axis, even if [b] is also equal to zero. The sign of [b] determines
- * the direction of the vector along the x-axis.
- *
- * Returns NaN if either argument is NaN.
- */
-external double atan2(num a, num b);
-
-/**
- * Returns [x] to the power of [exponent].
- *
- * If [x] is an [int] and [exponent] is a non-negative [int], the result is
- * an [int], otherwise the result it is a [double].
- *
- * Notice that an [int] result cannot overflow, but a [double] result might
- * be [double.INFINITY].
- */
-external num pow(num x, num exponent);
-
-/**
- * Converts [x] to a double and returns the sine of the value.
- *
- * If [x] is not a finite number, the result is NaN.
- */
-external double sin(num x);
-
-/**
- * Converts [x] to a double and returns the cosine of the value.
- *
- * If [x] is not a finite number, the result is NaN.
- */
-external double cos(num x);
-
-/**
- * Converts [x] to a double and returns the tangent of the value.
- *
- * The tangent function is equivalent to [:sin(x)/cos(x):] and may be
- * infinite (positive or negative) when [:cos(x):] is equal to zero.
- * If [x] is not a finite number, the result is NaN.
- */
-external double tan(num x);
-
-/**
- * Converts [x] to a double and returns the arc cosine of the value.
- *
- * Returns a value in the range -PI..PI, or NaN if [x] is outside
- * the range -1..1.
- */
-external double acos(num x);
-
-/**
- * Converts [x] to a double and returns the arc sine of the value.
- * Returns a value in the range -PI..PI, or  NaN if [x] is outside
- * the range -1..1.
- */
-external double asin(num x);
-
-/**
- * Converts [x] to a dobule and returns the arc tangent of the vlaue.
- * Returns a value in the range -PI/2..PI/2, or NaN if [x] is NaN.
- */
-external double atan(num x);
-
-/**
- * Converts [x] to a double and returns the positive square root of the value.
- *
- * Returns -0.0 if [x] is -0.0, and NaN if [x] is otherwise negative or NaN.
- */
-external double sqrt(num x);
-
-/**
- * Converts [x] to a double and returns the natural exponent, [E],
- * to the power [x].
- * Returns NaN if [x] is NaN.
- */
-external double exp(num x);
-
-/**
- * Converts [x] to a double and returns the natural logarithm of the value.
- * Returns negative infinity if [x] is equal to zero.
- * Returns NaN if [x] is NaN or less than zero.
- */
-external double log(num x);
diff --git a/sdk/lib/math/math.dart b/sdk/lib/math/math.dart
index 428f6ce..b6ac482 100644
--- a/sdk/lib/math/math.dart
+++ b/sdk/lib/math/math.dart
@@ -4,5 +4,220 @@
 
 library dart.math;
 
-part "base.dart";
 part "random.dart";
+
+/**
+ * Base of the natural logarithms.
+ *
+ * Typically written as "e".
+ */
+const double E = 2.718281828459045;
+
+/**
+ * Natural logarithm of 10.
+ */
+const double LN10 =  2.302585092994046;
+
+/**
+ * Natural logarithm of 2.
+ */
+const double LN2 =  0.6931471805599453;
+
+/**
+ * Base-2 logarithm of [E].
+ */
+const double LOG2E = 1.4426950408889634;
+
+/**
+ * Base-10 logarithm of [E].
+ */
+const double LOG10E = 0.4342944819032518;
+
+/**
+ * The PI constant.
+ */
+const double PI = 3.1415926535897932;
+
+/**
+ * Square root of 1/2.
+ */
+const double SQRT1_2 = 0.7071067811865476;
+
+/**
+ * Square root of 2.
+ */
+const double SQRT2 = 1.4142135623730951;
+
+/**
+  * Returns the lesser of two numbers.
+  *
+  * Returns NaN if either argument is NaN.
+  * The lesser of [:-0.0:] and [:0.0:] is [:-0.0:].
+  * If the arguments are otherwise equal (including int and doubles with the
+  * same mathematical value) then it is unspecified which of the two arguments
+  * is returned.
+  */
+num min(num a, num b) {
+  if (a is num) {
+    // TODO(floitsch): merge this if into the previous one, once dart2js
+    // correctly propagates types for logical ands.
+    if (b is num) {
+      if (a > b) return b;
+      if (a < b) return a;
+      if (b is double) {
+        // Special case for NaN and -0.0. If one argument is NaN return NaN.
+        // [min] must also distinguish between -0.0 and 0.0.
+        if (a is double) {
+          if (a == 0.0) {
+            // a is either 0.0 or -0.0. b is either 0.0, -0.0 or NaN.
+            // The following returns -0.0 if either a or b is -0.0, and it
+            // returns NaN if b is NaN.
+            return (a + b) * a * b;
+          }
+        }
+        // Check for NaN and b == -0.0.
+        if (a == 0 && b.isNegative || b.isNaN) return b;
+        return a;
+      }
+      return a;
+    }
+    throw new ArgumentError(b);
+  }
+  throw new ArgumentError(a);
+}
+
+/**
+  * Returns the larger of two numbers.
+  *
+  * Returns NaN if either argument is NaN.
+  * The larger of [:-0.0:] and [:0.0:] is [:0.0:]. If the arguments are
+  * otherwise equal (including int and doubles with the same mathematical value)
+  * then it is unspecified which of the two arguments is returned.
+  */
+num max(num a, num b) {
+  if (a is num) {
+    // TODO(floitsch): merge this if into the previous one, once dart2js
+    // correctly propagates types for logical ands.
+    if (b is num) {
+      if (a > b) return a;
+      if (a < b) return b;
+      if (b is double) {
+        // Special case for NaN and -0.0. If one argument is NaN return NaN.
+        // [max] must also distinguish between -0.0 and 0.0.
+        if (a is double) {
+          if (a == 0.0) {
+            // a is either 0.0 or -0.0. b is either 0.0, -0.0, or NaN.
+            // The following returns 0.0 if either a or b is 0.0, and it
+            // returns NaN if b is NaN.
+            return a + b;
+          }
+        }
+        // Check for NaN.
+        if (b.isNaN) return b;
+        return a;
+      }
+      // max(-0.0, 0) must return 0.
+      if (b == 0 && a.isNegative) return b;
+      return a;
+    }
+    throw new ArgumentError(b);
+  }
+  throw new ArgumentError(a);
+}
+
+/**
+ * A variant of [atan].
+ *
+ * Converts both arguments to doubles.
+ *
+ * Returns the angle between the positive x-axis and the vector ([b],[a]).
+ * The result, in radians, is in the range -PI..PI.
+ *
+ * If [b] is positive, this is the same as [:atan(b/a):].
+ *
+ * The result is negative when [a] is negative (including when [a] is the
+ * double -0.0).
+ *
+ * If [a] is equal to zero, the vector ([b],[a]) is considered parallel to
+ * the x-axis, even if [b] is also equal to zero. The sign of [b] determines
+ * the direction of the vector along the x-axis.
+ *
+ * Returns NaN if either argument is NaN.
+ */
+external double atan2(num a, num b);
+
+/**
+ * Returns [x] to the power of [exponent].
+ *
+ * If [x] is an [int] and [exponent] is a non-negative [int], the result is
+ * an [int], otherwise the result it is a [double].
+ *
+ * Notice that an [int] result cannot overflow, but a [double] result might
+ * be [double.INFINITY].
+ */
+external num pow(num x, num exponent);
+
+/**
+ * Converts [x] to a double and returns the sine of the value.
+ *
+ * If [x] is not a finite number, the result is NaN.
+ */
+external double sin(num x);
+
+/**
+ * Converts [x] to a double and returns the cosine of the value.
+ *
+ * If [x] is not a finite number, the result is NaN.
+ */
+external double cos(num x);
+
+/**
+ * Converts [x] to a double and returns the tangent of the value.
+ *
+ * The tangent function is equivalent to [:sin(x)/cos(x):] and may be
+ * infinite (positive or negative) when [:cos(x):] is equal to zero.
+ * If [x] is not a finite number, the result is NaN.
+ */
+external double tan(num x);
+
+/**
+ * Converts [x] to a double and returns the arc cosine of the value.
+ *
+ * Returns a value in the range -PI..PI, or NaN if [x] is outside
+ * the range -1..1.
+ */
+external double acos(num x);
+
+/**
+ * Converts [x] to a double and returns the arc sine of the value.
+ * Returns a value in the range -PI..PI, or  NaN if [x] is outside
+ * the range -1..1.
+ */
+external double asin(num x);
+
+/**
+ * Converts [x] to a dobule and returns the arc tangent of the vlaue.
+ * Returns a value in the range -PI/2..PI/2, or NaN if [x] is NaN.
+ */
+external double atan(num x);
+
+/**
+ * Converts [x] to a double and returns the positive square root of the value.
+ *
+ * Returns -0.0 if [x] is -0.0, and NaN if [x] is otherwise negative or NaN.
+ */
+external double sqrt(num x);
+
+/**
+ * Converts [x] to a double and returns the natural exponent, [E],
+ * to the power [x].
+ * Returns NaN if [x] is NaN.
+ */
+external double exp(num x);
+
+/**
+ * Converts [x] to a double and returns the natural logarithm of the value.
+ * Returns negative infinity if [x] is equal to zero.
+ * Returns NaN if [x] is NaN or less than zero.
+ */
+external double log(num x);
diff --git a/sdk/lib/math/math_sources.gypi b/sdk/lib/math/math_sources.gypi
index cbfad89..ed2577e 100644
--- a/sdk/lib/math/math_sources.gypi
+++ b/sdk/lib/math/math_sources.gypi
@@ -6,7 +6,6 @@
   'sources': [
     'math.dart',
     # The above file needs to be first as it lists the parts below.
-    'base.dart',
     'random.dart',
   ],
 }
diff --git a/sdk/lib/mirrors/mirrors.dart b/sdk/lib/mirrors/mirrors.dart
index 2a2ecea..70c523e 100644
--- a/sdk/lib/mirrors/mirrors.dart
+++ b/sdk/lib/mirrors/mirrors.dart
@@ -17,4 +17,752 @@
 import 'dart:async';
 import 'dart:isolate';
 
-part 'mirrors_impl.dart';
+/**
+ * A [MirrorSystem] is the main interface used to reflect on a set of
+ * associated libraries.
+ *
+ * At runtime each running isolate has a distinct [MirrorSystem].
+ *
+ * It is also possible to have a [MirrorSystem] which represents a set
+ * of libraries which are not running -- perhaps at compile-time.  In
+ * this case, all available reflective functionality would be
+ * supported, but runtime functionality (such as invoking a function
+ * or inspecting the contents of a variable) would fail dynamically.
+ */
+abstract class MirrorSystem {
+  /**
+   * An immutable map from from library names to mirrors for all
+   * libraries known to this mirror system.
+   */
+  Map<String, LibraryMirror> get libraries;
+
+  /**
+   * A mirror on the isolate associated with this [MirrorSystem].
+   * This may be null if this mirror system is not running.
+   */
+  IsolateMirror get isolate;
+
+  /**
+   * A mirror on the [:dynamic:] type.
+   */
+  TypeMirror get dynamicType;
+
+  /**
+   * A mirror on the [:void:] type.
+   */
+  TypeMirror get voidType;
+}
+
+/**
+ * Returns a [MirrorSystem] for the current isolate.
+ */
+external MirrorSystem currentMirrorSystem();
+
+/**
+ * Creates a [MirrorSystem] for the isolate which is listening on
+ * the [SendPort].
+ */
+external Future<MirrorSystem> mirrorSystemOf(SendPort port);
+
+/**
+ * Returns an [InstanceMirror] for some Dart language object.
+ *
+ * This only works if this mirror system is associated with the
+ * current running isolate.
+ */
+external InstanceMirror reflect(Object reflectee);
+
+/**
+ * A [Mirror] reflects some Dart language entity.
+ *
+ * Every [Mirror] originates from some [MirrorSystem].
+ */
+abstract class Mirror {
+  /**
+   * The [MirrorSystem] that contains this mirror.
+   */
+  MirrorSystem get mirrors;
+}
+
+/**
+ * An [IsolateMirror] reflects an isolate.
+ */
+abstract class IsolateMirror implements Mirror {
+  /**
+   * A unique name used to refer to an isolate in debugging messages.
+   */
+  String get debugName;
+
+  /**
+   * Does this mirror reflect the currently running isolate?
+   */
+  bool get isCurrent;
+
+  /**
+   * A mirror on the root library for this isolate.
+   */
+  LibraryMirror get rootLibrary;
+}
+
+/**
+ * A [DeclarationMirror] reflects some entity declared in a Dart program.
+ */
+abstract class DeclarationMirror implements Mirror {
+  /**
+   * The simple name for this Dart language entity.
+   *
+   * The simple name is in most cases the the identifier name of the
+   * entity, such as 'method' for a method [:void method() {...}:] or
+   * 'mylibrary' for a [:#library('mylibrary');:] declaration.
+   */
+  String get simpleName;
+
+  /**
+   * The fully-qualified name for this Dart language entity.
+   *
+   * This name is qualified by the name of the owner. For instance,
+   * the qualified name of a method 'method' in class 'Class' in
+   * library 'library' is 'library.Class.method'.
+   *
+   * TODO(turnidge): Specify whether this name is unique.  Currently
+   * this is a gray area due to lack of clarity over whether library
+   * names are unique.
+   */
+  String get qualifiedName;
+
+  /**
+   * A mirror on the owner of this function.  This is the declaration
+   * immediately surrounding the reflectee.
+   *
+   * Note that for libraries, the owner will be [:null:].
+   */
+  DeclarationMirror get owner;
+
+  /**
+   * Is this declaration private?
+   *
+   * Note that for libraries, this will be [:false:].
+   */
+  bool get isPrivate;
+
+  /**
+   * Is this declaration top-level?
+   *
+   * This is defined to be equivalent to:
+   *    [:mirror.owner != null && mirror.owner is LibraryMirror:]
+   */
+  bool get isTopLevel;
+
+  /**
+   * The source location of this Dart language entity.
+   */
+  SourceLocation get location;
+}
+
+/**
+ * An [ObjectMirror] is a common superinterface of [InstanceMirror],
+ * [ClassMirror], and [LibraryMirror] that represents their shared
+ * functionality.
+ *
+ * For the purposes of the mirrors library, these types are all
+ * object-like, in that they support method invocation and field
+ * access.  Real Dart objects are represented by the [InstanceMirror]
+ * type.
+ *
+ * See [InstanceMirror], [ClassMirror], and [LibraryMirror].
+ */
+abstract class ObjectMirror implements Mirror {
+  /**
+   * Invokes the named function and returns a mirror on the result.
+   *
+   * TODO(turnidge): Properly document.
+   * TODO(turnidge): Handle ambiguous names.
+   * TODO(turnidge): Handle optional & named arguments.
+   */
+  Future<InstanceMirror> invoke(String memberName,
+                                List<Object> positionalArguments,
+                                [Map<String,Object> namedArguments]);
+
+  /**
+   * Invokes a getter and returns a mirror on the result. The getter
+   * can be the implicit getter for a field or a user-defined getter
+   * method.
+   *
+   * TODO(turnidge): Handle ambiguous names.
+   */
+  Future<InstanceMirror> getField(String fieldName);
+
+  /**
+   * Invokes a setter and returns a mirror on the result. The setter
+   * may be either the implicit setter for a non-final field or a
+   * user-defined setter method.
+   *
+   * TODO(turnidge): Handle ambiguous names.
+   */
+  Future<InstanceMirror> setField(String fieldName, Object value);
+}
+
+/**
+ * An [InstanceMirror] reflects an instance of a Dart language object.
+ */
+abstract class InstanceMirror implements ObjectMirror {
+  /**
+   * A mirror on the type of the reflectee.
+   */
+  ClassMirror get type;
+
+  /**
+   * Does [reflectee] contain the instance reflected by this mirror?
+   * This will always be true in the local case (reflecting instances
+   * in the same isolate), but only true in the remote case if this
+   * mirror reflects a simple value.
+   *
+   * A value is simple if one of the following holds:
+   *  - the value is null
+   *  - the value is of type [num]
+   *  - the value is of type [bool]
+   *  - the value is of type [String]
+   */
+  bool get hasReflectee;
+
+  /**
+   * If the [InstanceMirror] reflects an instance it is meaningful to
+   * have a local reference to, we provide access to the actual
+   * instance here.
+   *
+   * If you access [reflectee] when [hasReflectee] is false, an
+   * exception is thrown.
+   */
+  get reflectee;
+}
+
+/**
+ * A [ClosureMirror] reflects a closure.
+ *
+ * A [ClosureMirror] provides access to its captured variables and
+ * provides the ability to execute its reflectee.
+ */
+abstract class ClosureMirror implements InstanceMirror {
+  /**
+   * A mirror on the function associated with this closure.
+   */
+  MethodMirror get function;
+
+  /**
+   * The source code for this closure, if available.  Otherwise null.
+   *
+   * TODO(turnidge): Would this just be available in function?
+   */
+  String get source;
+
+  /**
+   * Executes the closure. The arguments given in the descriptor need to
+   * be InstanceMirrors or simple values.
+   *
+   * A value is simple if one of the following holds:
+   *  - the value is null
+   *  - the value is of type [num]
+   *  - the value is of type [bool]
+   *  - the value is of type [String]
+   */
+  Future<InstanceMirror> apply(List<Object> positionalArguments,
+                               [Map<String,Object> namedArguments]);
+
+  /**
+   * Looks up the value of a name in the scope of the closure. The
+   * result is a mirror on that value.
+   */
+  Future<InstanceMirror> findInContext(String name);
+}
+
+/**
+ * A [LibraryMirror] reflects a Dart language library, providing
+ * access to the variables, functions, and classes of the
+ * library.
+ */
+abstract class LibraryMirror implements DeclarationMirror, ObjectMirror {
+  /**
+   * The url of the library.
+   *
+   * TODO(turnidge): Document where this url comes from.  Will this
+   * value be sensible?
+   */
+  String get url;
+
+  /**
+   * An immutable map from from names to mirrors for all members in
+   * this library.
+   *
+   * The members of a library are its top-level classes,
+   * functions, variables, getters, and setters.
+   */
+  Map<String, Mirror> get members;
+
+  /**
+   * An immutable map from names to mirrors for all class
+   * declarations in this library.
+   */
+  Map<String, ClassMirror> get classes;
+
+  /**
+   * An immutable map from names to mirrors for all function, getter,
+   * and setter declarations in this library.
+   */
+  Map<String, MethodMirror> get functions;
+
+  /**
+   * An immutable map from names to mirrors for all getter
+   * declarations in this library.
+   */
+  Map<String, MethodMirror> get getters;
+
+  /**
+   * An immutable map from names to mirrors for all setter
+   * declarations in this library.
+   */
+  Map<String, MethodMirror> get setters;
+
+  /**
+   * An immutable map from names to mirrors for all variable
+   * declarations in this library.
+   */
+  Map<String, VariableMirror> get variables;
+}
+
+/**
+ * A [TypeMirror] reflects a Dart language class, typedef
+ * or type variable.
+ */
+abstract class TypeMirror implements DeclarationMirror {
+}
+
+/**
+ * A [ClassMirror] reflects a Dart language class.
+ */
+abstract class ClassMirror implements TypeMirror, ObjectMirror {
+  /**
+   * A mirror on the superclass on the reflectee.
+   *
+   * If this type is [:Object:] or a typedef, the superClass will be
+   * null.
+   */
+  ClassMirror get superclass;
+
+  /**
+   * A list of mirrors on the superinterfaces of the reflectee.
+   */
+  List<ClassMirror> get superinterfaces;
+
+  /**
+   * An immutable map from from names to mirrors for all members of
+   * this type.
+   *
+   * The members of a type are its methods, fields, getters, and
+   * setters.  Note that constructors and type variables are not
+   * considered to be members of a type.
+   *
+   * This does not include inherited members.
+   */
+  Map<String, Mirror> get members;
+
+  /**
+   * An immutable map from names to mirrors for all method,
+   * declarations for this type.  This does not include getters and
+   * setters.
+   */
+  Map<String, MethodMirror> get methods;
+
+  /**
+   * An immutable map from names to mirrors for all getter
+   * declarations for this type.
+   */
+  Map<String, MethodMirror> get getters;
+
+  /**
+   * An immutable map from names to mirrors for all setter
+   * declarations for this type.
+   */
+  Map<String, MethodMirror> get setters;
+
+  /**
+   * An immutable map from names to mirrors for all variable
+   * declarations for this type.
+   */
+  Map<String, VariableMirror> get variables;
+
+  /**
+   * An immutable map from names to mirrors for all constructor
+   * declarations for this type.
+   */
+   Map<String, MethodMirror> get constructors;
+
+  /**
+   * An immutable map from names to mirrors for all type variables for
+   * this type.
+   *
+   * This map preserves the order of declaration of the type variables.
+   */
+   Map<String, TypeVariableMirror> get typeVariables;
+
+  /**
+   * An immutable map from names to mirrors for all type arguments for
+   * this type.
+   *
+   * This map preserves the order of declaration of the type variables.
+   */
+  Map<String, TypeMirror> get typeArguments;
+
+  /**
+   * Is this the original declaration of this type?
+   *
+   * For most classes, they are their own original declaration.  For
+   * generic classes, however, there is a distinction between the
+   * original class declaration, which has unbound type variables, and
+   * the instantiations of generic classes, which have bound type
+   * variables.
+   */
+  bool get isOriginalDeclaration;
+
+  /**
+   * A mirror on the original declaration of this type.
+   *
+   * For most classes, they are their own original declaration.  For
+   * generic classes, however, there is a distinction between the
+   * original class declaration, which has unbound type variables, and
+   * the instantiations of generic classes, which have bound type
+   * variables.
+   */
+  ClassMirror get originalDeclaration;
+
+  /**
+   * Invokes the named constructor and returns a mirror on the result.
+   *
+   * TODO(turnidge): Properly document.
+   */
+  Future<InstanceMirror> newInstance(String constructorName,
+                                     List<Object> positionalArguments,
+                                     [Map<String,Object> namedArguments]);
+
+  /**
+   * Does this mirror represent a class?
+   *
+   * TODO(turnidge): This functions goes away after the
+   * class/interface changes.
+   */
+  bool get isClass;
+
+  /**
+   * A mirror on the default factory class or null if there is none.
+   *
+   * TODO(turnidge): This functions goes away after the
+   * class/interface changes.
+   */
+  ClassMirror get defaultFactory;
+}
+
+/**
+ * A [FunctionTypeMirror] represents the type of a function in the
+ * Dart language.
+ */
+abstract class FunctionTypeMirror implements ClassMirror {
+  /**
+   * The return type of the reflectee.
+   */
+  TypeMirror get returnType;
+
+  /**
+   * A list of the parameter types of the reflectee.
+   */
+  List<ParameterMirror> get parameters;
+
+  /**
+   * A mirror on the [:call:] method for the reflectee.
+   *
+   * TODO(turnidge): What is this and what is it for?
+   */
+  MethodMirror get callMethod;
+}
+
+/**
+ * A [TypeVariableMirror] represents a type parameter of a generic
+ * type.
+ */
+abstract class TypeVariableMirror extends TypeMirror {
+  /**
+   * A mirror on the type that is the upper bound of this type variable.
+   */
+  TypeMirror get upperBound;
+}
+
+/**
+ * A [TypedefMirror] represents a typedef in a Dart language program.
+ */
+abstract class TypedefMirror implements ClassMirror {
+  /**
+   * The defining type for this typedef.
+   *
+   * For instance [:void f(int):] is the value for [:typedef void f(int):].
+   */
+  TypeMirror get value;
+}
+
+/**
+ * A [MethodMirror] reflects a Dart language function, method,
+ * constructor, getter, or setter.
+ */
+abstract class MethodMirror implements DeclarationMirror {
+  /**
+   * A mirror on the return type for the reflectee.
+   */
+  TypeMirror get returnType;
+
+  /**
+   * A list of mirrors on the parameters for the reflectee.
+   */
+  List<ParameterMirror> get parameters;
+
+  /**
+   * Is the reflectee static?
+   *
+   * For the purposes of the mirrors library, a top-level function is
+   * considered static.
+   */
+  bool get isStatic;
+
+  /**
+   * Is the reflectee abstract?
+   */
+  bool get isAbstract;
+
+  /**
+   * Is the reflectee a regular function or method?
+   *
+   * A function or method is regular if it is not a getter, setter, or
+   * constructor.  Note that operators, by this definition, are
+   * regular methods.
+   */
+  bool get isRegularMethod;
+
+  /**
+   * Is the reflectee an operator?
+   */
+  bool get isOperator;
+
+  /**
+   * Is the reflectee a getter?
+   */
+  bool get isGetter;
+
+  /**
+   * Is the reflectee a setter?
+   */
+  bool get isSetter;
+
+  /**
+   * Is the reflectee a constructor?
+   */
+  bool get isConstructor;
+
+  /**
+   * The constructor name for named constructors and factory methods.
+   *
+   * For unnamed constructors, this is the empty string.  For
+   * non-constructors, this is the empty string.
+   *
+   * For example, [:'bar':] is the constructor name for constructor
+   * [:Foo.bar:] of type [:Foo:].
+   */
+  String get constructorName;
+
+  /**
+   * Is the reflectee a const constructor?
+   */
+  bool get isConstConstructor;
+
+  /**
+   * Is the reflectee a generative constructor?
+   */
+  bool get isGenerativeConstructor;
+
+  /**
+   * Is the reflectee a redirecting constructor?
+   */
+  bool get isRedirectingConstructor;
+
+  /**
+   * Is the reflectee a factory constructor?
+   */
+  bool get isFactoryConstructor;
+}
+
+/**
+ * A [VariableMirror] reflects a Dart language variable declaration.
+ */
+abstract class VariableMirror implements DeclarationMirror {
+  /**
+   * A mirror on the type of the reflectee.
+   */
+  TypeMirror get type;
+
+  /**
+   * Is the reflectee a static variable?
+   *
+   * For the purposes of the mirror library, top-level variables are
+   * implicitly declared static.
+   */
+  bool get isStatic;
+
+  /**
+   * Is the reflectee a final variable?
+   */
+  bool get isFinal;
+}
+
+/**
+ * A [ParameterMirror] reflects a Dart formal parameter declaration.
+ */
+abstract class ParameterMirror implements VariableMirror {
+  /**
+   * A mirror on the type of this parameter.
+   */
+  TypeMirror get type;
+
+  /**
+   * Is this parameter optional?
+   */
+  bool get isOptional;
+
+  /**
+   * Is this parameter named?
+   */
+  bool get isNamed;
+
+  /**
+   * Does this parameter have a default value?
+   */
+  bool get hasDefaultValue;
+
+  /**
+   * A mirror on the default value for this parameter, if it exists.
+   *
+   * TODO(turnidge): String may not be a good representation of this
+   * at runtime.
+   */
+  String get defaultValue;
+}
+
+/**
+ * A [SourceLocation] describes the span of an entity in Dart source code.
+ */
+abstract class SourceLocation {
+}
+
+/**
+ * When an error occurs during the mirrored execution of code, a
+ * [MirroredError] is thrown.
+ *
+ * In general, there are three main classes of failure that can happen
+ * during mirrored execution of code in some isolate:
+ *
+ * - An exception is thrown but not caught.  This is caught by the
+ *   mirrors framework and a [MirroredUncaughtExceptionError] is
+ *   created and thrown.
+ *
+ * - A compile-time error occurs, such as a syntax error.  This is
+ *   suppressed by the mirrors framework and a
+ *   [MirroredCompilationError] is created and thrown.
+ *
+ * - A truly fatal error occurs, causing the isolate to be exited.  If
+ *   the reflector and reflectee share the same isolate, then they
+ *   will both suffer.  If the reflector and reflectee are in distinct
+ *   isolates, then we hope to provide some information about the
+ *   isolate death, but this has yet to be implemented.
+ *
+ * TODO(turnidge): Specify the behavior for remote fatal errors.
+ */
+abstract class MirroredError implements Exception {
+}
+
+/**
+ * When an uncaught exception occurs during the mirrored execution
+ * of code, a [MirroredUncaughtExceptionError] is thrown.
+ *
+ * This exception contains a mirror on the original exception object.
+ * It also contains an object which can be used to recover the
+ * stacktrace.
+ */
+class MirroredUncaughtExceptionError extends MirroredError {
+  MirroredUncaughtExceptionError(this.exception_mirror,
+                                 this.exception_string,
+                                 this.stacktrace) {}
+
+  /** A mirror on the exception object. */
+  final InstanceMirror exception_mirror;
+
+  /** The result of toString() for the exception object. */
+  final String exception_string;
+
+  /** A stacktrace object for the uncaught exception. */
+  final Object stacktrace;
+
+  String toString() {
+    return
+        "Uncaught exception during mirrored execution: <${exception_string}>";
+  }
+}
+
+/**
+ * When a compile-time error occurs during the mirrored execution
+ * of code, a [MirroredCompilationError] is thrown.
+ *
+ * This exception includes the compile-time error message that would
+ * have been displayed to the user, if the function had not been
+ * invoked via mirror.
+ */
+class MirroredCompilationError extends MirroredError {
+  MirroredCompilationError(this.message) {}
+
+  final String message;
+
+  String toString() {
+    return "Compile-time error during mirrored execution: <$message>";
+  }
+}
+
+/**
+ * A [MirrorException] is used to indicate errors within the mirrors
+ * framework.
+ */
+class MirrorException implements Exception {
+  const MirrorException(String this._message);
+  String toString() => "MirrorException: '$_message'";
+  final String _message;
+}
+
+/**
+ * Class used for encoding comments as metadata annotations.
+ */
+class Comment {
+  /**
+   * The comment text as written in the source text.
+   */
+  final String text;
+
+  /**
+   * The comment text without the start, end, and padding text.
+   *
+   * For example, if [text] is [: /** Comment text. */ :] then the [trimmedText]
+   * is [: Comment text. :].
+   */
+  final String trimmedText;
+
+  /**
+   * Is [:true:] if this comment is a documentation comment.
+   *
+   * That is, that the comment is either enclosed in [: /** ... */ :] or starts
+   * with [: /// :].
+   */
+  final bool isDocComment;
+
+  const Comment(this.text, this.trimmedText, this.isDocComment);
+}
diff --git a/sdk/lib/mirrors/mirrors_impl.dart b/sdk/lib/mirrors/mirrors_impl.dart
deleted file mode 100644
index b49c40e..0000000
--- a/sdk/lib/mirrors/mirrors_impl.dart
+++ /dev/null
@@ -1,755 +0,0 @@
-// Copyright (c) 2012, 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 dart.mirrors;
-
-/**
- * A [MirrorSystem] is the main interface used to reflect on a set of
- * associated libraries.
- *
- * At runtime each running isolate has a distinct [MirrorSystem].
- *
- * It is also possible to have a [MirrorSystem] which represents a set
- * of libraries which are not running -- perhaps at compile-time.  In
- * this case, all available reflective functionality would be
- * supported, but runtime functionality (such as invoking a function
- * or inspecting the contents of a variable) would fail dynamically.
- */
-abstract class MirrorSystem {
-  /**
-   * An immutable map from from library names to mirrors for all
-   * libraries known to this mirror system.
-   */
-  Map<String, LibraryMirror> get libraries;
-
-  /**
-   * A mirror on the isolate associated with this [MirrorSystem].
-   * This may be null if this mirror system is not running.
-   */
-  IsolateMirror get isolate;
-
-  /**
-   * A mirror on the [:dynamic:] type.
-   */
-  TypeMirror get dynamicType;
-
-  /**
-   * A mirror on the [:void:] type.
-   */
-  TypeMirror get voidType;
-}
-
-/**
- * Returns a [MirrorSystem] for the current isolate.
- */
-external MirrorSystem currentMirrorSystem();
-
-/**
- * Creates a [MirrorSystem] for the isolate which is listening on
- * the [SendPort].
- */
-external Future<MirrorSystem> mirrorSystemOf(SendPort port);
-
-/**
- * Returns an [InstanceMirror] for some Dart language object.
- *
- * This only works if this mirror system is associated with the
- * current running isolate.
- */
-external InstanceMirror reflect(Object reflectee);
-
-/**
- * A [Mirror] reflects some Dart language entity.
- *
- * Every [Mirror] originates from some [MirrorSystem].
- */
-abstract class Mirror {
-  /**
-   * The [MirrorSystem] that contains this mirror.
-   */
-  MirrorSystem get mirrors;
-}
-
-/**
- * An [IsolateMirror] reflects an isolate.
- */
-abstract class IsolateMirror implements Mirror {
-  /**
-   * A unique name used to refer to an isolate in debugging messages.
-   */
-  String get debugName;
-
-  /**
-   * Does this mirror reflect the currently running isolate?
-   */
-  bool get isCurrent;
-
-  /**
-   * A mirror on the root library for this isolate.
-   */
-  LibraryMirror get rootLibrary;
-}
-
-/**
- * A [DeclarationMirror] reflects some entity declared in a Dart program.
- */
-abstract class DeclarationMirror implements Mirror {
-  /**
-   * The simple name for this Dart language entity.
-   *
-   * The simple name is in most cases the the identifier name of the
-   * entity, such as 'method' for a method [:void method() {...}:] or
-   * 'mylibrary' for a [:#library('mylibrary');:] declaration.
-   */
-  String get simpleName;
-
-  /**
-   * The fully-qualified name for this Dart language entity.
-   *
-   * This name is qualified by the name of the owner. For instance,
-   * the qualified name of a method 'method' in class 'Class' in
-   * library 'library' is 'library.Class.method'.
-   *
-   * TODO(turnidge): Specify whether this name is unique.  Currently
-   * this is a gray area due to lack of clarity over whether library
-   * names are unique.
-   */
-  String get qualifiedName;
-
-  /**
-   * A mirror on the owner of this function.  This is the declaration
-   * immediately surrounding the reflectee.
-   *
-   * Note that for libraries, the owner will be [:null:].
-   */
-  DeclarationMirror get owner;
-
-  /**
-   * Is this declaration private?
-   *
-   * Note that for libraries, this will be [:false:].
-   */
-  bool get isPrivate;
-
-  /**
-   * Is this declaration top-level?
-   *
-   * This is defined to be equivalent to:
-   *    [:mirror.owner != null && mirror.owner is LibraryMirror:]
-   */
-  bool get isTopLevel;
-
-  /**
-   * The source location of this Dart language entity.
-   */
-  SourceLocation get location;
-}
-
-/**
- * An [ObjectMirror] is a common superinterface of [InstanceMirror],
- * [ClassMirror], and [LibraryMirror] that represents their shared
- * functionality.
- *
- * For the purposes of the mirrors library, these types are all
- * object-like, in that they support method invocation and field
- * access.  Real Dart objects are represented by the [InstanceMirror]
- * type.
- *
- * See [InstanceMirror], [ClassMirror], and [LibraryMirror].
- */
-abstract class ObjectMirror implements Mirror {
-  /**
-   * Invokes the named function and returns a mirror on the result.
-   *
-   * TODO(turnidge): Properly document.
-   * TODO(turnidge): Handle ambiguous names.
-   * TODO(turnidge): Handle optional & named arguments.
-   */
-  Future<InstanceMirror> invoke(String memberName,
-                                List<Object> positionalArguments,
-                                [Map<String,Object> namedArguments]);
-
-  /**
-   * Invokes a getter and returns a mirror on the result. The getter
-   * can be the implicit getter for a field or a user-defined getter
-   * method.
-   *
-   * TODO(turnidge): Handle ambiguous names.
-   */
-  Future<InstanceMirror> getField(String fieldName);
-
-  /**
-   * Invokes a setter and returns a mirror on the result. The setter
-   * may be either the implicit setter for a non-final field or a
-   * user-defined setter method.
-   *
-   * TODO(turnidge): Handle ambiguous names.
-   */
-  Future<InstanceMirror> setField(String fieldName, Object value);
-}
-
-/**
- * An [InstanceMirror] reflects an instance of a Dart language object.
- */
-abstract class InstanceMirror implements ObjectMirror {
-  /**
-   * A mirror on the type of the reflectee.
-   */
-  ClassMirror get type;
-
-  /**
-   * Does [reflectee] contain the instance reflected by this mirror?
-   * This will always be true in the local case (reflecting instances
-   * in the same isolate), but only true in the remote case if this
-   * mirror reflects a simple value.
-   *
-   * A value is simple if one of the following holds:
-   *  - the value is null
-   *  - the value is of type [num]
-   *  - the value is of type [bool]
-   *  - the value is of type [String]
-   */
-  bool get hasReflectee;
-
-  /**
-   * If the [InstanceMirror] reflects an instance it is meaningful to
-   * have a local reference to, we provide access to the actual
-   * instance here.
-   *
-   * If you access [reflectee] when [hasReflectee] is false, an
-   * exception is thrown.
-   */
-  get reflectee;
-}
-
-/**
- * A [ClosureMirror] reflects a closure.
- *
- * A [ClosureMirror] provides access to its captured variables and
- * provides the ability to execute its reflectee.
- */
-abstract class ClosureMirror implements InstanceMirror {
-  /**
-   * A mirror on the function associated with this closure.
-   */
-  MethodMirror get function;
-
-  /**
-   * The source code for this closure, if available.  Otherwise null.
-   *
-   * TODO(turnidge): Would this just be available in function?
-   */
-  String get source;
-
-  /**
-   * Executes the closure. The arguments given in the descriptor need to
-   * be InstanceMirrors or simple values.
-   *
-   * A value is simple if one of the following holds:
-   *  - the value is null
-   *  - the value is of type [num]
-   *  - the value is of type [bool]
-   *  - the value is of type [String]
-   */
-  Future<InstanceMirror> apply(List<Object> positionalArguments,
-                               [Map<String,Object> namedArguments]);
-
-  /**
-   * Looks up the value of a name in the scope of the closure. The
-   * result is a mirror on that value.
-   */
-  Future<InstanceMirror> findInContext(String name);
-}
-
-/**
- * A [LibraryMirror] reflects a Dart language library, providing
- * access to the variables, functions, and classes of the
- * library.
- */
-abstract class LibraryMirror implements DeclarationMirror, ObjectMirror {
-  /**
-   * The url of the library.
-   *
-   * TODO(turnidge): Document where this url comes from.  Will this
-   * value be sensible?
-   */
-  String get url;
-
-  /**
-   * An immutable map from from names to mirrors for all members in
-   * this library.
-   *
-   * The members of a library are its top-level classes,
-   * functions, variables, getters, and setters.
-   */
-  Map<String, Mirror> get members;
-
-  /**
-   * An immutable map from names to mirrors for all class
-   * declarations in this library.
-   */
-  Map<String, ClassMirror> get classes;
-
-  /**
-   * An immutable map from names to mirrors for all function, getter,
-   * and setter declarations in this library.
-   */
-  Map<String, MethodMirror> get functions;
-
-  /**
-   * An immutable map from names to mirrors for all getter
-   * declarations in this library.
-   */
-  Map<String, MethodMirror> get getters;
-
-  /**
-   * An immutable map from names to mirrors for all setter
-   * declarations in this library.
-   */
-  Map<String, MethodMirror> get setters;
-
-  /**
-   * An immutable map from names to mirrors for all variable
-   * declarations in this library.
-   */
-  Map<String, VariableMirror> get variables;
-}
-
-/**
- * A [TypeMirror] reflects a Dart language class, typedef
- * or type variable.
- */
-abstract class TypeMirror implements DeclarationMirror {
-}
-
-/**
- * A [ClassMirror] reflects a Dart language class.
- */
-abstract class ClassMirror implements TypeMirror, ObjectMirror {
-  /**
-   * A mirror on the superclass on the reflectee.
-   *
-   * If this type is [:Object:] or a typedef, the superClass will be
-   * null.
-   */
-  ClassMirror get superclass;
-
-  /**
-   * A list of mirrors on the superinterfaces of the reflectee.
-   */
-  List<ClassMirror> get superinterfaces;
-
-  /**
-   * An immutable map from from names to mirrors for all members of
-   * this type.
-   *
-   * The members of a type are its methods, fields, getters, and
-   * setters.  Note that constructors and type variables are not
-   * considered to be members of a type.
-   *
-   * This does not include inherited members.
-   */
-  Map<String, Mirror> get members;
-
-  /**
-   * An immutable map from names to mirrors for all method,
-   * declarations for this type.  This does not include getters and
-   * setters.
-   */
-  Map<String, MethodMirror> get methods;
-
-  /**
-   * An immutable map from names to mirrors for all getter
-   * declarations for this type.
-   */
-  Map<String, MethodMirror> get getters;
-
-  /**
-   * An immutable map from names to mirrors for all setter
-   * declarations for this type.
-   */
-  Map<String, MethodMirror> get setters;
-
-  /**
-   * An immutable map from names to mirrors for all variable
-   * declarations for this type.
-   */
-  Map<String, VariableMirror> get variables;
-
-  /**
-   * An immutable map from names to mirrors for all constructor
-   * declarations for this type.
-   */
-   Map<String, MethodMirror> get constructors;
-
-  /**
-   * An immutable map from names to mirrors for all type variables for
-   * this type.
-   *
-   * This map preserves the order of declaration of the type variables.
-   */
-   Map<String, TypeVariableMirror> get typeVariables;
-
-  /**
-   * An immutable map from names to mirrors for all type arguments for
-   * this type.
-   *
-   * This map preserves the order of declaration of the type variables.
-   */
-  Map<String, TypeMirror> get typeArguments;
-
-  /**
-   * Is this the original declaration of this type?
-   *
-   * For most classes, they are their own original declaration.  For
-   * generic classes, however, there is a distinction between the
-   * original class declaration, which has unbound type variables, and
-   * the instantiations of generic classes, which have bound type
-   * variables.
-   */
-  bool get isOriginalDeclaration;
-
-  /**
-   * A mirror on the original declaration of this type.
-   *
-   * For most classes, they are their own original declaration.  For
-   * generic classes, however, there is a distinction between the
-   * original class declaration, which has unbound type variables, and
-   * the instantiations of generic classes, which have bound type
-   * variables.
-   */
-  ClassMirror get originalDeclaration;
-
-  /**
-   * Invokes the named constructor and returns a mirror on the result.
-   *
-   * TODO(turnidge): Properly document.
-   */
-  Future<InstanceMirror> newInstance(String constructorName,
-                                     List<Object> positionalArguments,
-                                     [Map<String,Object> namedArguments]);
-
-  /**
-   * Does this mirror represent a class?
-   *
-   * TODO(turnidge): This functions goes away after the
-   * class/interface changes.
-   */
-  bool get isClass;
-
-  /**
-   * A mirror on the default factory class or null if there is none.
-   *
-   * TODO(turnidge): This functions goes away after the
-   * class/interface changes.
-   */
-  ClassMirror get defaultFactory;
-}
-
-/**
- * A [FunctionTypeMirror] represents the type of a function in the
- * Dart language.
- */
-abstract class FunctionTypeMirror implements ClassMirror {
-  /**
-   * The return type of the reflectee.
-   */
-  TypeMirror get returnType;
-
-  /**
-   * A list of the parameter types of the reflectee.
-   */
-  List<ParameterMirror> get parameters;
-
-  /**
-   * A mirror on the [:call:] method for the reflectee.
-   *
-   * TODO(turnidge): What is this and what is it for?
-   */
-  MethodMirror get callMethod;
-}
-
-/**
- * A [TypeVariableMirror] represents a type parameter of a generic
- * type.
- */
-abstract class TypeVariableMirror extends TypeMirror {
-  /**
-   * A mirror on the type that is the upper bound of this type variable.
-   */
-  TypeMirror get upperBound;
-}
-
-/**
- * A [TypedefMirror] represents a typedef in a Dart language program.
- */
-abstract class TypedefMirror implements ClassMirror {
-  /**
-   * The defining type for this typedef.
-   *
-   * For instance [:void f(int):] is the value for [:typedef void f(int):].
-   */
-  TypeMirror get value;
-}
-
-/**
- * A [MethodMirror] reflects a Dart language function, method,
- * constructor, getter, or setter.
- */
-abstract class MethodMirror implements DeclarationMirror {
-  /**
-   * A mirror on the return type for the reflectee.
-   */
-  TypeMirror get returnType;
-
-  /**
-   * A list of mirrors on the parameters for the reflectee.
-   */
-  List<ParameterMirror> get parameters;
-
-  /**
-   * Is the reflectee static?
-   *
-   * For the purposes of the mirrors library, a top-level function is
-   * considered static.
-   */
-  bool get isStatic;
-
-  /**
-   * Is the reflectee abstract?
-   */
-  bool get isAbstract;
-
-  /**
-   * Is the reflectee a regular function or method?
-   *
-   * A function or method is regular if it is not a getter, setter, or
-   * constructor.  Note that operators, by this definition, are
-   * regular methods.
-   */
-  bool get isRegularMethod;
-
-  /**
-   * Is the reflectee an operator?
-   */
-  bool get isOperator;
-
-  /**
-   * Is the reflectee a getter?
-   */
-  bool get isGetter;
-
-  /**
-   * Is the reflectee a setter?
-   */
-  bool get isSetter;
-
-  /**
-   * Is the reflectee a constructor?
-   */
-  bool get isConstructor;
-
-  /**
-   * The constructor name for named constructors and factory methods.
-   *
-   * For unnamed constructors, this is the empty string.  For
-   * non-constructors, this is the empty string.
-   *
-   * For example, [:'bar':] is the constructor name for constructor
-   * [:Foo.bar:] of type [:Foo:].
-   */
-  String get constructorName;
-
-  /**
-   * Is the reflectee a const constructor?
-   */
-  bool get isConstConstructor;
-
-  /**
-   * Is the reflectee a generative constructor?
-   */
-  bool get isGenerativeConstructor;
-
-  /**
-   * Is the reflectee a redirecting constructor?
-   */
-  bool get isRedirectingConstructor;
-
-  /**
-   * Is the reflectee a factory constructor?
-   */
-  bool get isFactoryConstructor;
-}
-
-/**
- * A [VariableMirror] reflects a Dart language variable declaration.
- */
-abstract class VariableMirror implements DeclarationMirror {
-  /**
-   * A mirror on the type of the reflectee.
-   */
-  TypeMirror get type;
-
-  /**
-   * Is the reflectee a static variable?
-   *
-   * For the purposes of the mirror library, top-level variables are
-   * implicitly declared static.
-   */
-  bool get isStatic;
-
-  /**
-   * Is the reflectee a final variable?
-   */
-  bool get isFinal;
-}
-
-/**
- * A [ParameterMirror] reflects a Dart formal parameter declaration.
- */
-abstract class ParameterMirror implements VariableMirror {
-  /**
-   * A mirror on the type of this parameter.
-   */
-  TypeMirror get type;
-
-  /**
-   * Is this parameter optional?
-   */
-  bool get isOptional;
-
-  /**
-   * Is this parameter named?
-   */
-  bool get isNamed;
-
-  /**
-   * Does this parameter have a default value?
-   */
-  bool get hasDefaultValue;
-
-  /**
-   * A mirror on the default value for this parameter, if it exists.
-   *
-   * TODO(turnidge): String may not be a good representation of this
-   * at runtime.
-   */
-  String get defaultValue;
-}
-
-/**
- * A [SourceLocation] describes the span of an entity in Dart source code.
- */
-abstract class SourceLocation {
-}
-
-/**
- * When an error occurs during the mirrored execution of code, a
- * [MirroredError] is thrown.
- *
- * In general, there are three main classes of failure that can happen
- * during mirrored execution of code in some isolate:
- *
- * - An exception is thrown but not caught.  This is caught by the
- *   mirrors framework and a [MirroredUncaughtExceptionError] is
- *   created and thrown.
- *
- * - A compile-time error occurs, such as a syntax error.  This is
- *   suppressed by the mirrors framework and a
- *   [MirroredCompilationError] is created and thrown.
- *
- * - A truly fatal error occurs, causing the isolate to be exited.  If
- *   the reflector and reflectee share the same isolate, then they
- *   will both suffer.  If the reflector and reflectee are in distinct
- *   isolates, then we hope to provide some information about the
- *   isolate death, but this has yet to be implemented.
- *
- * TODO(turnidge): Specify the behavior for remote fatal errors.
- */
-abstract class MirroredError implements Exception {
-}
-
-/**
- * When an uncaught exception occurs during the mirrored execution
- * of code, a [MirroredUncaughtExceptionError] is thrown.
- *
- * This exception contains a mirror on the original exception object.
- * It also contains an object which can be used to recover the
- * stacktrace.
- */
-class MirroredUncaughtExceptionError extends MirroredError {
-  MirroredUncaughtExceptionError(this.exception_mirror,
-                                 this.exception_string,
-                                 this.stacktrace) {}
-
-  /** A mirror on the exception object. */
-  final InstanceMirror exception_mirror;
-
-  /** The result of toString() for the exception object. */
-  final String exception_string;
-
-  /** A stacktrace object for the uncaught exception. */
-  final Object stacktrace;
-
-  String toString() {
-    return
-        "Uncaught exception during mirrored execution: <${exception_string}>";
-  }
-}
-
-/**
- * When a compile-time error occurs during the mirrored execution
- * of code, a [MirroredCompilationError] is thrown.
- *
- * This exception includes the compile-time error message that would
- * have been displayed to the user, if the function had not been
- * invoked via mirror.
- */
-class MirroredCompilationError extends MirroredError {
-  MirroredCompilationError(this.message) {}
-
-  final String message;
-
-  String toString() {
-    return "Compile-time error during mirrored execution: <$message>";
-  }
-}
-
-/**
- * A [MirrorException] is used to indicate errors within the mirrors
- * framework.
- */
-class MirrorException implements Exception {
-  const MirrorException(String this._message);
-  String toString() => "MirrorException: '$_message'";
-  final String _message;
-}
-
-/**
- * Class used for encoding comments as metadata annotations.
- */
-class Comment {
-  /**
-   * The comment text as written in the source text.
-   */
-  final String text;
-
-  /**
-   * The comment text without the start, end, and padding text.
-   *
-   * For example, if [text] is [: /** Comment text. */ :] then the [trimmedText]
-   * is [: Comment text. :].
-   */
-  final String trimmedText;
-
-  /**
-   * Is [:true:] if this comment is a documentation comment.
-   *
-   * That is, that the comment is either enclosed in [: /** ... */ :] or starts
-   * with [: /// :].
-   */
-  final bool isDocComment;
-
-  const Comment(this.text, this.trimmedText, this.isDocComment);
-}
diff --git a/sdk/lib/mirrors/mirrors_sources.gypi b/sdk/lib/mirrors/mirrors_sources.gypi
index 73d1620..8c97af5 100644
--- a/sdk/lib/mirrors/mirrors_sources.gypi
+++ b/sdk/lib/mirrors/mirrors_sources.gypi
@@ -5,7 +5,6 @@
 {
   'sources': [
     'mirrors.dart',
-    # The above file needs to be first as it lists the parts below.
-    'mirrors_impl.dart',
+    # The above file needs to be first if additional parts are added to the lib.
   ],
 }
diff --git a/sdk/lib/scalarlist/byte_arrays.dart b/sdk/lib/scalarlist/byte_arrays.dart
index e37efc2..d843259 100644
--- a/sdk/lib/scalarlist/byte_arrays.dart
+++ b/sdk/lib/scalarlist/byte_arrays.dart
@@ -269,30 +269,6 @@
   int setUint64(int byteOffset, int value);
 
   /**
-   * Returns the Float32x4 number represented by the 16 bytes at
-   * the specified [byteOffset] in this byte array.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 16` is greater than the length of this byte array.
-   */
-  Float32x4 getFloat32x4(int byteOffset);
-
-  /**
-   * Sets the sixteen bytes starting at the specified [byteOffset] in this
-   * byte array to the Float32x4 representation of the specified [value].
-   *
-   *
-   * Returns `byteOffset + 16`, which is the offset of the first byte in the
-   * array after the last byte that was set by this call. This return value can
-   * be passed as the [byteOffset] parameter to a subsequent `setXxx` call.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 16` is greater than the length of this byte array.
-   */
-  int setFloat32x4(int byteOffset, Float32x4 value);
-
-
-  /**
    * Returns the floating point number represented by the four bytes at
    * the specified [byteOffset] in this byte array, in IEEE 754
    * single-precision binary floating-point format (binary32).
diff --git a/sdk/lib/scalarlist/scalarlist.dart b/sdk/lib/scalarlist/scalarlist.dart
index 9d79daa..34c8ca8 100644
--- a/sdk/lib/scalarlist/scalarlist.dart
+++ b/sdk/lib/scalarlist/scalarlist.dart
@@ -14,5 +14,4 @@
 
 import 'dart:collection';
 
-part 'byte_arrays.dart';
-part 'simd128.dart';
\ No newline at end of file
+part 'byte_arrays.dart';
\ No newline at end of file
diff --git a/sdk/lib/scalarlist/scalarlist_sources.gypi b/sdk/lib/scalarlist/scalarlist_sources.gypi
index b04d10d..92e0f24 100644
--- a/sdk/lib/scalarlist/scalarlist_sources.gypi
+++ b/sdk/lib/scalarlist/scalarlist_sources.gypi
@@ -7,6 +7,5 @@
     'scalarlist.dart',
     # The above file needs to be first as it lists the parts below.
     'byte_arrays.dart',
-    'simd128.dart',
   ],
 }
diff --git a/sdk/lib/scalarlist/simd128.dart b/sdk/lib/scalarlist/simd128.dart
deleted file mode 100644
index 96349fd..0000000
--- a/sdk/lib/scalarlist/simd128.dart
+++ /dev/null
@@ -1,188 +0,0 @@
-// Copyright (c) 2013, 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 dart.scalarlist;
-
-/**
- * Interface of Dart Float32x4 and operations.
- * Float32x4 stores 4 32-bit floating point values in "lanes".
- * The lanes are "x", "y", "z", and "w" respectively.
- */
-abstract class Float32x4 {
-  external factory Float32x4(double x, double y, double z, double w);
-  external factory Float32x4.zero();
-
-  /// Addition operator.
-  Float32x4 operator+(Float32x4 other);
-  /// Negate operator.
-  Float32x4 operator-();
-  /// Subtraction operator.
-  Float32x4 operator-(Float32x4 other);
-  /// Multiplication operator.
-  Float32x4 operator*(Float32x4 other);
-  /// Division operator.
-  Float32x4 operator/(Float32x4 other);
-
-  /// Relational less than.
-  Uint32x4 lessThan(Float32x4 other);
-  /// Relational less than or equal.
-  Uint32x4 lessThanOrEqual(Float32x4 other);
-  /// Relational greater than.
-  Uint32x4 greaterThan(Float32x4 other);
-  /// Relational greater than or equal.
-  Uint32x4 greaterThanOrEqual(Float32x4 other);
-  /// Relational equal.
-  Uint32x4 equal(Float32x4 other);
-  /// Relational not-equal.
-  Uint32x4 notEqual(Float32x4 other);
-
-  /// Returns a copy of [this] each lane being scaled by [s].
-  Float32x4 scale(double s);
-  /// Returns the absolute value of this [Simd128Float32].
-  Float32x4 abs();
-  /// Clamps [this] to be in the range [lowerLimit]-[upperLimit].
-  Float32x4 clamp(Float32x4 lowerLimit,
-                         Float32x4 upperLimit);
-
-  /// Extracted x value.
-  double get x;
-  /// Extracted y value.
-  double get y;
-  /// Extracted z value.
-  double get z;
-  /// Extracted w value.
-  double get w;
-
-  /// Returns a new [Float32x4] with [this]' x value in all four lanes.
-  Float32x4 get xxxx;
-  /// Returns a new [Float32x4] with [this]' y value in all four lanes.
-  Float32x4 get yyyy;
-  /// Returns a new [Float32x4] with [this]' z value in all four lanes.
-  Float32x4 get zzzz;
-  /// Returns a new [Float32x4] with [this]' w value in all four lanes.
-  Float32x4 get wwww;
-  // TODO(johnmccutchan): Add all 256 possible combinations.
-
-  /// Returns a new [Float32x4] copied from [this] with a new x value.
-  Float32x4 withX(double x);
-  /// Returns a new [Float32x4] copied from [this] with a new y value.
-  Float32x4 withY(double y);
-  /// Returns a new [Float32x4] copied from [this] with a new z value.
-  Float32x4 withZ(double z);
-  /// Returns a new [Float32x4] copied from [this] with a new w value.
-  Float32x4 withW(double w);
-
-  /// Returns the lane-wise minimum value in [this] or [other].
-  Float32x4 min(Float32x4 other);
-
-  /// Returns the lane-wise maximum value in [this] or [other].
-  Float32x4 max(Float32x4 other);
-
-  /// Returns the square root of [this].
-  Float32x4 sqrt();
-
-  /// Returns the reciprocal of [this].
-  Float32x4 reciprocal();
-
-  /// Returns the square root of the reciprocal of [this].
-  Float32x4 reciprocalSqrt();
-
-  /// Returns a bit-wise copy of [this] as a [Uint32x4].
-  Uint32x4 toUint32x4();
-}
-
-/**
- * Interface of Dart Uint32x4 and operations.
- * Uint32x4 stores 4 32-bit bit-masks in "lanes".
- * The lanes are "x", "y", "z", and "w" respectively.
- */
-abstract class Uint32x4 {
-  external factory Uint32x4(int x, int y, int z, int w);
-  external factory Uint32x4.bool(bool x, bool y, bool z, bool w);
-
-  /// The bit-wise or operator.
-  Uint32x4 operator|(Uint32x4 other);
-  /// The bit-wise and operator.
-  Uint32x4 operator&(Uint32x4 other);
-  /// The bit-wise xor operator.
-  Uint32x4 operator^(Uint32x4 other);
-
-  /// Extract 32-bit mask from x lane.
-  int get x;
-  /// Extract 32-bit mask from y lane.
-  int get y;
-  /// Extract 32-bit mask from z lane.
-  int get z;
-  /// Extract 32-bit mask from w lane.
-  int get w;
-
-  /// Returns a new [Uint32x4] copied from [this] with a new x value.
-  Uint32x4 withX(int x);
-  /// Returns a new [Uint32x4] copied from [this] with a new y value.
-  Uint32x4 withY(int y);
-  /// Returns a new [Uint32x4] copied from [this] with a new z value.
-  Uint32x4 withZ(int z);
-  /// Returns a new [Uint32x4] copied from [this] with a new w value.
-  Uint32x4 withW(int w);
-
-  /// Extracted x value. Returns false for 0, true for any other value.
-  bool get flagX;
-  /// Extracted y value. Returns false for 0, true for any other value.
-  bool get flagY;
-  /// Extracted z value. Returns false for 0, true for any other value.
-  bool get flagZ;
-  /// Extracted w value. Returns false for 0, true for any other value.
-  bool get flagW;
-
-  /// Returns a new [Uint32x4] copied from [this] with a new x value.
-  Uint32x4 withFlagX(bool x);
-  /// Returns a new [Uint32x4] copied from [this] with a new y value.
-  Uint32x4 withFlagY(bool y);
-  /// Returns a new [Uint32x4] copied from [this] with a new z value.
-  Uint32x4 withFlagZ(bool z);
-  /// Returns a new [Uint32x4] copied from [this] with a new w value.
-  Uint32x4 withFlagW(bool w);
-
-  /// Merge [trueValue] and [falseValue] based on [this]' bit mask:
-  /// Select bit from [trueValue] when bit in [this] is on.
-  /// Select bit from [falseValue] when bit in [this] is off.
-  Float32x4 select(Float32x4 trueValue, Float32x4 falseValue);
-
-  /// Returns a bit-wise copy of [this] as a [Float32x4].
-  Float32x4 toFloat32x4();
-}
-
-/**
- * A fixed-length list of Float32x4 numbers that is viewable as a
- * [ByteArray]. For long lists, this implementation will be considerably more
- * space- and time-efficient than the default [List] implementation.
- */
-abstract class Float32x4List implements List<Float32x4>,
-    ByteArrayViewable {
-  /**
-   * Creates a [Simd128Float32List] of the specified length (in elements),
-   * all of whose elements are initially zero.
-   */
-  external factory Float32x4List(int length);
-
-  /**
-   * Creates a [Float32x4List] _view_ of the specified region in the
-   * specified byte [array]. Changes in the [Float32x4List] will be
-   * visible in the byte array and vice versa. If the [start] index of the
-   * region is not specified, it defaults to zero (the first byte in the byte
-   * array). If the length is not specified, it defaults to null, which
-   * indicates that the view extends to the end of the byte array.
-   *
-   * Throws [ArgumentError] if the length of the specified region is not
-   * divisible by 16 (the size of a "Float32x4" in bytes), or if the
-   * [start] of the region is not divisible by 16. If, however, [array] is a
-   * view of another byte array, this constructor will throw [ArgumentError]
-   * if the implicit starting position in the "ultimately backing" byte array
-   * is not divisible by 16. In plain terms, this constructor throws
-   * [ArgumentError] if the specified region does not contain an integral
-   * number of "Float32x4s," or if it is not "Float32x4-aligned."
-   */
-  external factory Float32x4List.view(ByteArray array,
-                                      [int start = 0, int length]);
-}
diff --git a/sdk/lib/typeddata/typeddata.dart b/sdk/lib/typeddata/typeddata.dart
index efaf880..773d3cc 100644
--- a/sdk/lib/typeddata/typeddata.dart
+++ b/sdk/lib/typeddata/typeddata.dart
@@ -6,4 +6,863 @@
 
 import 'dart:collection';
 
-part 'typeddata_base.dart';
+/**
+ * A sequence of bytes underlying a typed data object.
+ * Used to process large quantities of binary or numerical data
+ * more efficiently using a typed view.
+ */
+abstract class ByteBuffer {
+  /**
+   * Returns the length of this byte buffer, in bytes.
+   */
+  int get lengthInBytes;
+
+}
+
+
+/**
+ * A typed view of a sequence of bytes.
+ */
+abstract class TypedData {
+  /**
+   * Returns the number of bytes in the representation of each element in this
+   * list.
+   */
+  int get elementSizeInBytes;
+
+  /**
+   * Returns the offset in bytes into the underlying byte buffer of this view.
+   */
+  int get offsetInBytes;
+
+  /**
+   * Returns the length of this view, in bytes.
+   */
+  int get lengthInBytes;
+
+  /**
+   * Returns the byte buffer associated with this object.
+   */
+  ByteBuffer get buffer;
+}
+
+
+/**
+ * A fixed-length, random-access sequence of bytes that also provides random
+ * and unaligned access to the fixed-width integers and floating point
+ * numbers represented by those bytes.
+ * ByteData may be used to pack and unpack data from external sources
+ * (such as networks or files systems), and to process large quantities
+ * of numerical data more efficiently than would be possible
+ * with ordinary [List] implementations. ByteData can save space, by
+ * eliminating the need for object headers, and time, by eliminating the
+ * need for data copies. Finally, ByteData may be used to intentionally
+ * reinterpret the bytes representing one arithmetic type as another.
+ * For example this code fragment determine what 32-bit signed integer
+ * is represented by the bytes of a 32-bit floating point number:
+ *
+ *     var buffer = new Uint8List(8).buffer;
+ *     var bdata = new ByteData.view(buffer);
+ *     bdata.setFloat32(0, 3.04);
+ *     int huh = bdata.getInt32(0);
+ */
+abstract class ByteData implements TypedData {
+  /**
+   * Creates a [ByteData] of the specified length (in elements), all of
+   * whose elements are initially zero.
+   */
+  external factory ByteData(int length);
+
+  /**
+   * Creates an [ByteData] _view_ of the specified region in the specified
+   * byte buffer. Changes in the [ByteData] will be visible in the byte
+   * buffer and vice versa. If the [offsetInBytes] index of the region is not
+   * specified, it defaults to zero (the first byte in the byte buffer).
+   * If the length is not specified, it defaults to null, which indicates
+   * that the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   */
+  external factory ByteData.view(ByteBuffer buffer,
+                                 [int offsetInBytes = 0, int length]);
+
+  /**
+   * Returns the (possibly negative) integer represented by the byte at the
+   * specified [byteOffset] in this object, in two's complement binary
+   * representation. The return value will be between -128 and 127, inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * greater than or equal to the length of this object.
+   */
+  int getInt8(int byteOffset);
+
+  /**
+   * Sets the byte at the specified [byteOffset] in this object to the
+   * two's complement binary representation of the specified [value], which
+   * must fit in a single byte. In other words, [value] must be between
+   * -128 and 127, inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * greater than or equal to the length of this object.
+   */
+  void setInt8(int byteOffset, int value);
+
+  /**
+   * Returns the positive integer represented by the byte at the specified
+   * [byteOffset] in this object, in unsigned binary form. The
+   * return value will be between 0 and 255, inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * greater than or equal to the length of this object.
+   */
+  int getUint8(int byteOffset);
+
+  /**
+   * Sets the byte at the specified [byteOffset] in this object to the
+   * unsigned binary representation of the specified [value], which must fit
+   * in a single byte. in other words, [value] must be between 0 and 255,
+   * inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative,
+   * or greater than or equal to the length of this object.
+   */
+  void setUint8(int byteOffset, int value);
+
+  /**
+   * Returns the (possibly negative) integer represented by the two bytes at
+   * the specified [byteOffset] in this object, in two's complement binary
+   * form.
+   * The return value will be between 2<sup>15</sup> and 2<sup>15</sup> - 1,
+   * inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 2` is greater than the length of this object.
+   */
+  int getInt16(int byteOffset);
+
+  /**
+   * Sets the two bytes starting at the specified [byteOffset] in this
+   * object to the two's complement binary representation of the specified
+   * [value], which must fit in two bytes. In other words, [value] must lie
+   * between 2<sup>15</sup> and 2<sup>15</sup> - 1, inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 2` is greater than the length of this object.
+   */
+  void setInt16(int byteOffset, int value);
+
+  /**
+   * Returns the positive integer represented by the two bytes starting
+   * at the specified [byteOffset] in this object, in unsigned binary
+   * form.
+   * The return value will be between 0 and  2<sup>16</sup> - 1, inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 2` is greater than the length of this object.
+   */
+  int getUint16(int byteOffset);
+
+  /**
+   * Sets the two bytes starting at the specified [byteOffset] in this object
+   * to the unsigned binary representation of the specified [value],
+   * which must fit in two bytes. in other words, [value] must be between
+   * 0 and 2<sup>16</sup> - 1, inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 2` is greater than the length of this object.
+   */
+  void setUint16(int byteOffset, int value);
+
+  /**
+   * Returns the (possibly negative) integer represented by the four bytes at
+   * the specified [byteOffset] in this object, in two's complement binary
+   * form.
+   * The return value will be between 2<sup>31</sup> and 2<sup>31</sup> - 1,
+   * inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 4` is greater than the length of this object.
+   */
+  int getInt32(int byteOffset);
+
+  /**
+   * Sets the four bytes starting at the specified [byteOffset] in this
+   * object to the two's complement binary representation of the specified
+   * [value], which must fit in four bytes. In other words, [value] must lie
+   * between 2<sup>31</sup> and 2<sup>31</sup> - 1, inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 4` is greater than the length of this object.
+   */
+  void setInt32(int byteOffset, int value);
+
+  /**
+   * Returns the positive integer represented by the four bytes starting
+   * at the specified [byteOffset] in this object, in unsigned binary
+   * form.
+   * The return value will be between 0 and  2<sup>32</sup> - 1, inclusive.
+   *
+   */
+  int getUint32(int byteOffset);
+
+  /**
+   * Sets the four bytes starting at the specified [byteOffset] in this object
+   * to the unsigned binary representation of the specified [value],
+   * which must fit in four bytes. in other words, [value] must be between
+   * 0 and 2<sup>32</sup> - 1, inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 4` is greater than the length of this object.
+   */
+  void setUint32(int byteOffset, int value);
+
+  /**
+   * Returns the (possibly negative) integer represented by the eight bytes at
+   * the specified [byteOffset] in this object, in two's complement binary
+   * form.
+   * The return value will be between 2<sup>63</sup> and 2<sup>63</sup> - 1,
+   * inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 8` is greater than the length of this object.
+   */
+  int getInt64(int byteOffset);
+
+  /**
+   * Sets the eight bytes starting at the specified [byteOffset] in this
+   * object to the two's complement binary representation of the specified
+   * [value], which must fit in eight bytes. In other words, [value] must lie
+   * between 2<sup>63</sup> and 2<sup>63</sup> - 1, inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 8` is greater than the length of this object.
+   */
+  void setInt64(int byteOffset, int value);
+
+  /**
+   * Returns the positive integer represented by the eight bytes starting
+   * at the specified [byteOffset] in this object, in unsigned binary
+   * form.
+   * The return value will be between 0 and  2<sup>64</sup> - 1, inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 8` is greater than the length of this object.
+   */
+  int getUint64(int byteOffset);
+
+  /**
+   * Sets the eight bytes starting at the specified [byteOffset] in this object
+   * to the unsigned binary representation of the specified [value],
+   * which must fit in eight bytes. in other words, [value] must be between
+   * 0 and 2<sup>64</sup> - 1, inclusive.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 8` is greater than the length of this object.
+   */
+  void setUint64(int byteOffset, int value);
+
+  /**
+   * Returns the floating point number represented by the four bytes at
+   * the specified [byteOffset] in this object, in IEEE 754
+   * single-precision binary floating-point format (binary32).
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 4` is greater than the length of this object.
+   */
+  double getFloat32(int byteOffset);
+
+  /**
+   * Sets the four bytes starting at the specified [byteOffset] in this
+   * object to the IEEE 754 single-precision binary floating-point
+   * (binary32) representation of the specified [value].
+   *
+   * **Note that this method can lose precision.** The input [value] is
+   * a 64-bit floating point value, which will be converted to 32-bit
+   * floating point value by IEEE 754 rounding rules before it is stored.
+   * If [value] cannot be represented exactly as a binary32, it will be
+   * converted to the nearest binary32 value.  If two binary32 values are
+   * equally close, the one whose least significant bit is zero will be used.
+   * Note that finite (but large) values can be converted to infinity, and
+   * small non-zero values can be converted to zero.
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 4` is greater than the length of this object.
+   */
+  void setFloat32(int byteOffset, double value);
+
+  /**
+   * Returns the floating point number represented by the eight bytes at
+   * the specified [byteOffset] in this object, in IEEE 754
+   * double-precision binary floating-point format (binary64).
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 8` is greater than the length of this object.
+   */
+  double getFloat64(int byteOffset);
+
+  /**
+   * Sets the eight bytes starting at the specified [byteOffset] in this
+   * object to the IEEE 754 double-precision binary floating-point
+   * (binary64) representation of the specified [value].
+   *
+   * Throws [RangeError] if [byteOffset] is negative, or
+   * `byteOffset + 8` is greater than the length of this object.
+   */
+  void setFloat64(int byteOffset, double value);
+}
+
+
+/**
+ * A fixed-length list of 8-bit signed integers.
+ * For long lists, this implementation can be considerably
+ * more space- and time-efficient than the default [List] implementation.
+ */
+abstract class Int8List implements List<int>, TypedData {
+  /**
+   * Creates an [Int8List] of the specified length (in elements), all of
+   * whose elements are initially zero.
+   */
+  external factory Int8List(int length);
+
+  /**
+   * Creates an [Int8List] _view_ of the specified region in the specified
+   * byte buffer. Changes in the [Int8List] will be visible in the byte
+   * buffer and vice versa. If the [offsetInBytes] index of the region is not
+   * specified, it defaults to zero (the first byte in the byte buffer).
+   * If the length is not specified, it defaults to null, which indicates
+   * that the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   */
+  external factory Int8List.view(ByteBuffer buffer,
+                                 [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 1;
+}
+
+
+/**
+ * A fixed-length list of 8-bit unsigned integers.
+ * For long lists, this implementation can be considerably
+ * more space- and time-efficient than the default [List] implementation.
+ */
+abstract class Uint8List implements List<int>, TypedData {
+  /**
+   * Creates a [Uint8List] of the specified length (in elements), all of
+   * whose elements are initially zero.
+   */
+  external factory Uint8List(int length);
+
+  /**
+   * Creates a [Uint8List] _view_ of the specified region in the specified
+   * byte buffer. Changes in the [Uint8List] will be visible in the byte
+   * buffer and vice versa. If the [offsetInBytes] index of the region is not
+   * specified, it defaults to zero (the first byte in the byte buffer).
+   * If the length is not specified, it defaults to null, which indicates
+   * that the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   */
+  external factory Uint8List.view(ByteBuffer buffer,
+                                  [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 1;
+}
+
+
+/**
+ * A fixed-length list of 8-bit unsigned integers.
+ * For long lists, this implementation can be considerably
+ * more space- and time-efficient than the default [List] implementation.
+ * Indexed store clamps the value to range 0..0xFF.
+ */
+abstract class Uint8ClampedList implements List<int>, TypedData {
+  /**
+   * Creates a [Uint8ClampedList] of the specified length (in elements), all of
+   * whose elements are initially zero.
+   */
+  external factory Uint8ClampedList(int length);
+
+  /**
+   * Creates a [Uint8ClampedList] _view_ of the specified region in the
+   * specified byte [buffer]. Changes in the [Uint8List] will be visible in the
+   * byte buffer and vice versa. If the [offsetInBytes] index of the region is
+   * not specified, it defaults to zero (the first byte in the byte buffer).
+   * If the length is not specified, it defaults to null, which indicates that
+   * the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   */
+  external factory Uint8ClampedList.view(ByteBuffer buffer,
+                                         [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 1;
+}
+
+
+/**
+ * A fixed-length list of 16-bit signed integers that is viewable as a
+ * [TypedData]. For long lists, this implementation can be considerably
+ * more space- and time-efficient than the default [List] implementation.
+ */
+abstract class Int16List implements List<int>, TypedData {
+  /**
+   * Creates an [Int16List] of the specified length (in elements), all of
+   * whose elements are initially zero.
+   */
+  external factory Int16List(int length);
+
+  /**
+   * Creates an [Int16List] _view_ of the specified region in the specified
+   * byte buffer. Changes in the [Int16List] will be visible in the byte
+   * buffer and vice versa. If the [offsetInBytes] index of the region is not
+   * specified, it defaults to zero (the first byte in the byte buffer).
+   * If the length is not specified, it defaults to null, which indicates
+   * that the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   *
+   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
+   * BYTES_PER_ELEMENT.
+   */
+  external factory Int16List.view(ByteBuffer buffer,
+                                  [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 2;
+}
+
+
+/**
+ * A fixed-length list of 16-bit unsigned integers that is viewable as a
+ * [TypedData]. For long lists, this implementation can be considerably
+ * more space- and time-efficient than the default [List] implementation.
+ */
+abstract class Uint16List implements List<int>, TypedData {
+  /**
+   * Creates a [Uint16List] of the specified length (in elements), all
+   * of whose elements are initially zero.
+   */
+  external factory Uint16List(int length);
+
+  /**
+   * Creates a [Uint16List] _view_ of the specified region in
+   * the specified byte buffer. Changes in the [Uint16List] will be
+   * visible in the byte buffer and vice versa. If the [offsetInBytes] index
+   * of the region is not specified, it defaults to zero (the first byte in
+   * the byte buffer). If the length is not specified, it defaults to null,
+   * which indicates that the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   *
+   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
+   * BYTES_PER_ELEMENT.
+   */
+  external factory Uint16List.view(ByteBuffer buffer,
+                                   [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 2;
+}
+
+
+/**
+ * A fixed-length list of 32-bit signed integers that is viewable as a
+ * [TypedData]. For long lists, this implementation can be considerably
+ * more space- and time-efficient than the default [List] implementation.
+ */
+abstract class Int32List implements List<int>, TypedData {
+  /**
+   * Creates an [Int32List] of the specified length (in elements), all of
+   * whose elements are initially zero.
+   */
+  external factory Int32List(int length);
+
+  /**
+   * Creates an [Int32List] _view_ of the specified region in the specified
+   * byte buffer. Changes in the [Int32List] will be visible in the byte
+   * buffer and vice versa. If the [offsetInBytes] index of the region is not
+   * specified, it defaults to zero (the first byte in the byte buffer).
+   * If the length is not specified, it defaults to null, which indicates
+   * that the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   *
+   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
+   * BYTES_PER_ELEMENT.
+   */
+  external factory Int32List.view(ByteBuffer buffer,
+                                  [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 4;
+}
+
+
+/**
+ * A fixed-length list of 32-bit unsigned integers that is viewable as a
+ * [TypedData]. For long lists, this implementation can be considerably
+ * more space- and time-efficient than the default [List] implementation.
+ */
+abstract class Uint32List implements List<int>, TypedData {
+  /**
+   * Creates a [Uint32List] of the specified length (in elements), all
+   * of whose elements are initially zero.
+   */
+  external factory Uint32List(int length);
+
+  /**
+   * Creates a [Uint32List] _view_ of the specified region in
+   * the specified byte buffer. Changes in the [Uint32] will be
+   * visible in the byte buffer and vice versa. If the [offsetInBytes] index
+   * of the region is not specified, it defaults to zero (the first byte in
+   * the byte buffer). If the length is not specified, it defaults to null,
+   * which indicates that the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   *
+   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
+   * BYTES_PER_ELEMENT.
+   */
+  external factory Uint32List.view(ByteBuffer buffer,
+                                   [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 4;
+}
+
+
+/**
+ * A fixed-length list of 64-bit signed integers that is viewable as a
+ * [TypedData]. For long lists, this implementation can be considerably
+ * more space- and time-efficient than the default [List] implementation.
+ */
+abstract class Int64List implements List<int>, TypedData {
+  /**
+   * Creates an [Int64List] of the specified length (in elements), all of
+   * whose elements are initially zero.
+   */
+  external factory Int64List(int length);
+
+  /**
+   * Creates an [Int64List] _view_ of the specified region in the specified
+   * byte buffer. Changes in the [Int64List] will be visible in the byte buffer
+   * and vice versa. If the [offsetInBytes] index of the region is not
+   * specified, it defaults to zero (the first byte in the byte buffer).
+   * If the length is not specified, it defaults to null, which indicates that
+   * the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   *
+   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
+   * BYTES_PER_ELEMENT.
+   */
+  external factory Int64List.view(ByteBuffer buffer,
+                                  [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 8;
+}
+
+
+/**
+ * A fixed-length list of 64-bit unsigned integers that is viewable as a
+ * [TypedData]. For long lists, this implementation can be considerably
+ * more space- and time-efficient than the default [List] implementation.
+ */
+abstract class Uint64List implements List<int>, TypedData {
+  /**
+   * Creates a [Uint64List] of the specified length (in elements), all
+   * of whose elements are initially zero.
+   */
+  external factory Uint64List(int length);
+
+  /**
+   * Creates an [Uint64List] _view_ of the specified region in
+   * the specified byte buffer. Changes in the [Uint64List] will be
+   * visible in the byte buffer and vice versa. If the [offsetInBytes]
+   * index of the region is not specified, it defaults to zero (the first
+   * byte in the byte buffer). If the length is not specified, it defaults
+   * to null, which indicates that the view extends to the end of the byte
+   * buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   *
+   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
+   * BYTES_PER_ELEMENT.
+   */
+  external factory Uint64List.view(ByteBuffer buffer,
+                                   [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 8;
+}
+
+
+/**
+ * A fixed-length list of IEEE 754 single-precision binary floating-point
+ * numbers  that is viewable as a [TypedData]. For long lists, this
+ * implementation can be considerably more space- and time-efficient than
+ * the default [List] implementation.
+ */
+abstract class Float32List implements List<double>, TypedData {
+  /**
+   * Creates a [Float32List] of the specified length (in elements), all of
+   * whose elements are initially zero.
+   */
+  external factory Float32List(int length);
+
+  /**
+   * Creates a [Float32List] _view_ of the specified region in the specified
+   * byte buffer. Changes in the [Float32List] will be visible in the byte
+   * buffer and vice versa. If the [offsetInBytes] index of the region is not
+   * specified, it defaults to zero (the first byte in the byte buffer).
+   * If the length is not specified, it defaults to null, which indicates
+   * that the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   *
+   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
+   * BYTES_PER_ELEMENT.
+   */
+  external factory Float32List.view(ByteBuffer buffer,
+                                    [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 4;
+}
+
+
+/**
+ * A fixed-length list of IEEE 754 double-precision binary floating-point
+ * numbers  that is viewable as a [TypedData]. For long lists, this
+ * implementation can be considerably more space- and time-efficient than
+ * the default [List] implementation.
+ */
+abstract class Float64List implements List<double>, TypedData {
+  /**
+   * Creates a [Float64List] of the specified length (in elements), all of
+   * whose elements are initially zero.
+   */
+  external factory Float64List(int length);
+
+  /**
+   * Creates a [Float64List] _view_ of the specified region in the specified
+   * byte buffer. Changes in the [Float64List] will be visible in the byte
+   * buffer and vice versa. If the [offsetInBytes] index of the region is not
+   * specified, it defaults to zero (the first byte in the byte buffer).
+   * If the length is not specified, it defaults to null, which indicates
+   * that the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   *
+   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
+   * BYTES_PER_ELEMENT.
+   */
+  external factory Float64List.view(ByteBuffer buffer,
+                                    [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 8;
+}
+
+
+/**
+ * A fixed-length list of Float32x4 numbers that is viewable as a
+ * [TypedData]. For long lists, this implementation will be considerably more
+ * space- and time-efficient than the default [List] implementation.
+ */
+abstract class Float32x4List implements List<Float32x4>, TypedData {
+  /**
+   * Creates a [Float32x4List] of the specified length (in elements),
+   * all of whose elements are initially zero.
+   */
+  external factory Float32x4List(int length);
+
+  /**
+   * Creates a [Float32x4List] _view_ of the specified region in the specified
+   * byte buffer. Changes in the [Float32x4List] will be visible in the byte
+   * buffer and vice versa. If the [offsetInBytes] index of the region is not
+   * specified, it defaults to zero (the first byte in the byte buffer).
+   * If the length is not specified, it defaults to null, which indicates
+   * that the view extends to the end of the byte buffer.
+   *
+   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
+   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
+   * the length of [buffer].
+   *
+   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
+   * BYTES_PER_ELEMENT.
+   */
+  external factory Float32x4List.view(ByteBuffer buffer,
+                                      [int offsetInBytes = 0, int length]);
+
+  static const int BYTES_PER_ELEMENT = 16;
+}
+
+
+/**
+ * Interface of Dart Float32x4 immutable value type and operations.
+ * Float32x4 stores 4 32-bit floating point values in "lanes".
+ * The lanes are "x", "y", "z", and "w" respectively.
+ */
+abstract class Float32x4 {
+  external factory Float32x4(double x, double y, double z, double w);
+  external factory Float32x4.zero();
+
+  /// Addition operator.
+  Float32x4 operator+(Float32x4 other);
+  /// Negate operator.
+  Float32x4 operator-();
+  /// Subtraction operator.
+  Float32x4 operator-(Float32x4 other);
+  /// Multiplication operator.
+  Float32x4 operator*(Float32x4 other);
+  /// Division operator.
+  Float32x4 operator/(Float32x4 other);
+
+  /// Relational less than.
+  Uint32x4 lessThan(Float32x4 other);
+  /// Relational less than or equal.
+  Uint32x4 lessThanOrEqual(Float32x4 other);
+  /// Relational greater than.
+  Uint32x4 greaterThan(Float32x4 other);
+  /// Relational greater than or equal.
+  Uint32x4 greaterThanOrEqual(Float32x4 other);
+  /// Relational equal.
+  Uint32x4 equal(Float32x4 other);
+  /// Relational not-equal.
+  Uint32x4 notEqual(Float32x4 other);
+
+  /// Returns a copy of [this] each lane being scaled by [s].
+  Float32x4 scale(double s);
+  /// Returns the absolute value of this [Float32x4].
+  Float32x4 abs();
+  /// Clamps [this] to be in the range [lowerLimit]-[upperLimit].
+  Float32x4 clamp(Float32x4 lowerLimit,
+                         Float32x4 upperLimit);
+
+  /// Extracted x value.
+  double get x;
+  /// Extracted y value.
+  double get y;
+  /// Extracted z value.
+  double get z;
+  /// Extracted w value.
+  double get w;
+
+  /// Returns a new [Float32x4] with [this]' x value in all four lanes.
+  Float32x4 get xxxx;
+  /// Returns a new [Float32x4] with [this]' y value in all four lanes.
+  Float32x4 get yyyy;
+  /// Returns a new [Float32x4] with [this]' z value in all four lanes.
+  Float32x4 get zzzz;
+  /// Returns a new [Float32x4] with [this]' w value in all four lanes.
+  Float32x4 get wwww;
+  // TODO(johnmccutchan): Add all 256 possible combinations.
+
+  /// Returns a new [Float32x4] copied from [this] with a new x value.
+  Float32x4 withX(double x);
+  /// Returns a new [Float32x4] copied from [this] with a new y value.
+  Float32x4 withY(double y);
+  /// Returns a new [Float32x4] copied from [this] with a new z value.
+  Float32x4 withZ(double z);
+  /// Returns a new [Float32x4] copied from [this] with a new w value.
+  Float32x4 withW(double w);
+
+  /// Returns the lane-wise minimum value in [this] or [other].
+  Float32x4 min(Float32x4 other);
+
+  /// Returns the lane-wise maximum value in [this] or [other].
+  Float32x4 max(Float32x4 other);
+
+  /// Returns the square root of [this].
+  Float32x4 sqrt();
+
+  /// Returns the reciprocal of [this].
+  Float32x4 reciprocal();
+
+  /// Returns the square root of the reciprocal of [this].
+  Float32x4 reciprocalSqrt();
+
+  /// Returns a bit-wise copy of [this] as a [Uint32x4].
+  Uint32x4 toUint32x4();
+}
+
+
+/**
+ * Interface of Dart Uint32x4 and operations.
+ * Uint32x4 stores 4 32-bit bit-masks in "lanes".
+ * The lanes are "x", "y", "z", and "w" respectively.
+ */
+abstract class Uint32x4 {
+  external factory Uint32x4(int x, int y, int z, int w);
+  external factory Uint32x4.bool(bool x, bool y, bool z, bool w);
+
+  /// The bit-wise or operator.
+  Uint32x4 operator|(Uint32x4 other);
+  /// The bit-wise and operator.
+  Uint32x4 operator&(Uint32x4 other);
+  /// The bit-wise xor operator.
+  Uint32x4 operator^(Uint32x4 other);
+
+  /// Extract 32-bit mask from x lane.
+  int get x;
+  /// Extract 32-bit mask from y lane.
+  int get y;
+  /// Extract 32-bit mask from z lane.
+  int get z;
+  /// Extract 32-bit mask from w lane.
+  int get w;
+
+  /// Returns a new [Uint32x4] copied from [this] with a new x value.
+  Uint32x4 withX(int x);
+  /// Returns a new [Uint32x4] copied from [this] with a new y value.
+  Uint32x4 withY(int y);
+  /// Returns a new [Uint32x4] copied from [this] with a new z value.
+  Uint32x4 withZ(int z);
+  /// Returns a new [Uint32x4] copied from [this] with a new w value.
+  Uint32x4 withW(int w);
+
+  /// Extracted x value. Returns false for 0, true for any other value.
+  bool get flagX;
+  /// Extracted y value. Returns false for 0, true for any other value.
+  bool get flagY;
+  /// Extracted z value. Returns false for 0, true for any other value.
+  bool get flagZ;
+  /// Extracted w value. Returns false for 0, true for any other value.
+  bool get flagW;
+
+  /// Returns a new [Uint32x4] copied from [this] with a new x value.
+  Uint32x4 withFlagX(bool x);
+  /// Returns a new [Uint32x4] copied from [this] with a new y value.
+  Uint32x4 withFlagY(bool y);
+  /// Returns a new [Uint32x4] copied from [this] with a new z value.
+  Uint32x4 withFlagZ(bool z);
+  /// Returns a new [Uint32x4] copied from [this] with a new w value.
+  Uint32x4 withFlagW(bool w);
+
+  /// Merge [trueValue] and [falseValue] based on [this]' bit mask:
+  /// Select bit from [trueValue] when bit in [this] is on.
+  /// Select bit from [falseValue] when bit in [this] is off.
+  Float32x4 select(Float32x4 trueValue, Float32x4 falseValue);
+
+  /// Returns a bit-wise copy of [this] as a [Float32x4].
+  Float32x4 toFloat32x4();
+}
diff --git a/sdk/lib/typeddata/typeddata_base.dart b/sdk/lib/typeddata/typeddata_base.dart
deleted file mode 100644
index f40c403..0000000
--- a/sdk/lib/typeddata/typeddata_base.dart
+++ /dev/null
@@ -1,681 +0,0 @@
-// Copyright (c) 2013, 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 dart.typeddata;
-
-/**
- * A sequence of bytes underlying a typed data object.
- * Used to process large quantities of binary or numerical data
- * more efficiently using a typed view.
- */
-abstract class ByteBuffer {
-  /**
-   * Returns the length of this byte buffer, in bytes.
-   */
-  int get lengthInBytes;
-
-}
-
-
-/**
- * A typed view of a sequence of bytes.
- */
-abstract class TypedData {
-  /**
-   * Returns the number of bytes in the representation of each element in this
-   * list.
-   */
-  int get elementSizeInBytes;
-
-  /**
-   * Returns the offset in bytes into the underlying byte buffer of this view.
-   */
-  int get offsetInBytes;
-
-  /**
-   * Returns the length of this view, in bytes.
-   */
-  int get lengthInBytes;
-
-  /**
-   * Returns the byte buffer associated with this object.
-   */
-  ByteBuffer get buffer;
-}
-
-
-/**
- * A fixed-length, random-access sequence of bytes that also provides random
- * and unaligned access to the fixed-width integers and floating point
- * numbers represented by those bytes.
- * ByteData may be used to pack and unpack data from external sources
- * (such as networks or files systems), and to process large quantities
- * of numerical data more efficiently than would be possible
- * with ordinary [List] implementations. ByteData can save space, by
- * eliminating the need for object headers, and time, by eliminating the
- * need for data copies. Finally, ByteData may be used to intentionally
- * reinterpret the bytes representing one arithmetic type as another.
- * For example this code fragment determine what 32-bit signed integer
- * is represented by the bytes of a 32-bit floating point number:
- *
- *     var buffer = new Uint8List(8).buffer;
- *     var bdata = new ByteData.view(buffer);
- *     bdata.setFloat32(0, 3.04);
- *     int huh = bdata.getInt32(0);
- */
-abstract class ByteData implements TypedData {
-  /**
-   * Creates a [ByteData] of the specified length (in elements), all of
-   * whose elements are initially zero.
-   */
-  external factory ByteData(int length);
-
-  /**
-   * Creates an [ByteData] _view_ of the specified region in the specified
-   * byte buffer. Changes in the [ByteData] will be visible in the byte
-   * buffer and vice versa. If the [offsetInBytes] index of the region is not
-   * specified, it defaults to zero (the first byte in the byte buffer).
-   * If the length is not specified, it defaults to null, which indicates
-   * that the view extends to the end of the byte buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   */
-  external factory ByteData.view(ByteBuffer buffer,
-                                 [int offsetInBytes = 0, int length]);
-
-  /**
-   * Returns the (possibly negative) integer represented by the byte at the
-   * specified [byteOffset] in this object, in two's complement binary
-   * representation. The return value will be between -128 and 127, inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * greater than or equal to the length of this object.
-   */
-  int getInt8(int byteOffset);
-
-  /**
-   * Sets the byte at the specified [byteOffset] in this object to the
-   * two's complement binary representation of the specified [value], which
-   * must fit in a single byte. In other words, [value] must be between
-   * -128 and 127, inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * greater than or equal to the length of this object.
-   */
-  void setInt8(int byteOffset, int value);
-
-  /**
-   * Returns the positive integer represented by the byte at the specified
-   * [byteOffset] in this object, in unsigned binary form. The
-   * return value will be between 0 and 255, inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * greater than or equal to the length of this object.
-   */
-  int getUint8(int byteOffset);
-
-  /**
-   * Sets the byte at the specified [byteOffset] in this object to the
-   * unsigned binary representation of the specified [value], which must fit
-   * in a single byte. in other words, [value] must be between 0 and 255,
-   * inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative,
-   * or greater than or equal to the length of this object.
-   */
-  void setUint8(int byteOffset, int value);
-
-  /**
-   * Returns the (possibly negative) integer represented by the two bytes at
-   * the specified [byteOffset] in this object, in two's complement binary
-   * form.
-   * The return value will be between 2<sup>15</sup> and 2<sup>15</sup> - 1,
-   * inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 2` is greater than the length of this object.
-   */
-  int getInt16(int byteOffset);
-
-  /**
-   * Sets the two bytes starting at the specified [byteOffset] in this
-   * object to the two's complement binary representation of the specified
-   * [value], which must fit in two bytes. In other words, [value] must lie
-   * between 2<sup>15</sup> and 2<sup>15</sup> - 1, inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 2` is greater than the length of this object.
-   */
-  void setInt16(int byteOffset, int value);
-
-  /**
-   * Returns the positive integer represented by the two bytes starting
-   * at the specified [byteOffset] in this object, in unsigned binary
-   * form.
-   * The return value will be between 0 and  2<sup>16</sup> - 1, inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 2` is greater than the length of this object.
-   */
-  int getUint16(int byteOffset);
-
-  /**
-   * Sets the two bytes starting at the specified [byteOffset] in this object
-   * to the unsigned binary representation of the specified [value],
-   * which must fit in two bytes. in other words, [value] must be between
-   * 0 and 2<sup>16</sup> - 1, inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 2` is greater than the length of this object.
-   */
-  void setUint16(int byteOffset, int value);
-
-  /**
-   * Returns the (possibly negative) integer represented by the four bytes at
-   * the specified [byteOffset] in this object, in two's complement binary
-   * form.
-   * The return value will be between 2<sup>31</sup> and 2<sup>31</sup> - 1,
-   * inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 4` is greater than the length of this object.
-   */
-  int getInt32(int byteOffset);
-
-  /**
-   * Sets the four bytes starting at the specified [byteOffset] in this
-   * object to the two's complement binary representation of the specified
-   * [value], which must fit in four bytes. In other words, [value] must lie
-   * between 2<sup>31</sup> and 2<sup>31</sup> - 1, inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 4` is greater than the length of this object.
-   */
-  void setInt32(int byteOffset, int value);
-
-  /**
-   * Returns the positive integer represented by the four bytes starting
-   * at the specified [byteOffset] in this object, in unsigned binary
-   * form.
-   * The return value will be between 0 and  2<sup>32</sup> - 1, inclusive.
-   *
-   */
-  int getUint32(int byteOffset);
-
-  /**
-   * Sets the four bytes starting at the specified [byteOffset] in this object
-   * to the unsigned binary representation of the specified [value],
-   * which must fit in four bytes. in other words, [value] must be between
-   * 0 and 2<sup>32</sup> - 1, inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 4` is greater than the length of this object.
-   */
-  void setUint32(int byteOffset, int value);
-
-  /**
-   * Returns the (possibly negative) integer represented by the eight bytes at
-   * the specified [byteOffset] in this object, in two's complement binary
-   * form.
-   * The return value will be between 2<sup>63</sup> and 2<sup>63</sup> - 1,
-   * inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 8` is greater than the length of this object.
-   */
-  int getInt64(int byteOffset);
-
-  /**
-   * Sets the eight bytes starting at the specified [byteOffset] in this
-   * object to the two's complement binary representation of the specified
-   * [value], which must fit in eight bytes. In other words, [value] must lie
-   * between 2<sup>63</sup> and 2<sup>63</sup> - 1, inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 8` is greater than the length of this object.
-   */
-  void setInt64(int byteOffset, int value);
-
-  /**
-   * Returns the positive integer represented by the eight bytes starting
-   * at the specified [byteOffset] in this object, in unsigned binary
-   * form.
-   * The return value will be between 0 and  2<sup>64</sup> - 1, inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 8` is greater than the length of this object.
-   */
-  int getUint64(int byteOffset);
-
-  /**
-   * Sets the eight bytes starting at the specified [byteOffset] in this object
-   * to the unsigned binary representation of the specified [value],
-   * which must fit in eight bytes. in other words, [value] must be between
-   * 0 and 2<sup>64</sup> - 1, inclusive.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 8` is greater than the length of this object.
-   */
-  void setUint64(int byteOffset, int value);
-
-  /**
-   * Returns the floating point number represented by the four bytes at
-   * the specified [byteOffset] in this object, in IEEE 754
-   * single-precision binary floating-point format (binary32).
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 4` is greater than the length of this object.
-   */
-  double getFloat32(int byteOffset);
-
-  /**
-   * Sets the four bytes starting at the specified [byteOffset] in this
-   * object to the IEEE 754 single-precision binary floating-point
-   * (binary32) representation of the specified [value].
-   *
-   * **Note that this method can lose precision.** The input [value] is
-   * a 64-bit floating point value, which will be converted to 32-bit
-   * floating point value by IEEE 754 rounding rules before it is stored.
-   * If [value] cannot be represented exactly as a binary32, it will be
-   * converted to the nearest binary32 value.  If two binary32 values are
-   * equally close, the one whose least significant bit is zero will be used.
-   * Note that finite (but large) values can be converted to infinity, and
-   * small non-zero values can be converted to zero.
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 4` is greater than the length of this object.
-   */
-  void setFloat32(int byteOffset, double value);
-
-  /**
-   * Returns the floating point number represented by the eight bytes at
-   * the specified [byteOffset] in this object, in IEEE 754
-   * double-precision binary floating-point format (binary64).
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 8` is greater than the length of this object.
-   */
-  double getFloat64(int byteOffset);
-
-  /**
-   * Sets the eight bytes starting at the specified [byteOffset] in this
-   * object to the IEEE 754 double-precision binary floating-point
-   * (binary64) representation of the specified [value].
-   *
-   * Throws [RangeError] if [byteOffset] is negative, or
-   * `byteOffset + 8` is greater than the length of this object.
-   */
-  void setFloat64(int byteOffset, double value);
-}
-
-
-/**
- * A fixed-length list of 8-bit signed integers.
- * For long lists, this implementation can be considerably
- * more space- and time-efficient than the default [List] implementation.
- */
-abstract class Int8List implements List<int>, TypedData {
-  /**
-   * Creates an [Int8List] of the specified length (in elements), all of
-   * whose elements are initially zero.
-   */
-  external factory Int8List(int length);
-
-  /**
-   * Creates an [Int8List] _view_ of the specified region in the specified
-   * byte buffer. Changes in the [Int8List] will be visible in the byte
-   * buffer and vice versa. If the [offsetInBytes] index of the region is not
-   * specified, it defaults to zero (the first byte in the byte buffer).
-   * If the length is not specified, it defaults to null, which indicates
-   * that the view extends to the end of the byte buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   */
-  external factory Int8List.view(ByteBuffer buffer,
-                                 [int offsetInBytes = 0, int length]);
-
-  static const int BYTES_PER_ELEMENT = 1;
-}
-
-
-/**
- * A fixed-length list of 8-bit unsigned integers.
- * For long lists, this implementation can be considerably
- * more space- and time-efficient than the default [List] implementation.
- */
-abstract class Uint8List implements List<int>, TypedData {
-  /**
-   * Creates a [Uint8List] of the specified length (in elements), all of
-   * whose elements are initially zero.
-   */
-  external factory Uint8List(int length);
-
-  /**
-   * Creates a [Uint8List] _view_ of the specified region in the specified
-   * byte buffer. Changes in the [Uint8List] will be visible in the byte
-   * buffer and vice versa. If the [offsetInBytes] index of the region is not
-   * specified, it defaults to zero (the first byte in the byte buffer).
-   * If the length is not specified, it defaults to null, which indicates
-   * that the view extends to the end of the byte buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   */
-  external factory Uint8List.view(ByteBuffer buffer,
-                                  [int offsetInBytes = 0, int length]);
-
-  static const int BYTES_PER_ELEMENT = 1;
-}
-
-
-/**
- * A fixed-length list of 8-bit unsigned integers.
- * For long lists, this implementation can be considerably
- * more space- and time-efficient than the default [List] implementation.
- * Indexed store clamps the value to range 0..0xFF.
- */
-abstract class Uint8ClampedList implements List<int>, TypedData {
-  /**
-   * Creates a [Uint8ClampedList] of the specified length (in elements), all of
-   * whose elements are initially zero.
-   */
-  external factory Uint8ClampedList(int length);
-
-  /**
-   * Creates a [Uint8ClampedList] _view_ of the specified region in the
-   * specified byte [buffer]. Changes in the [Uint8List] will be visible in the
-   * byte buffer and vice versa. If the [offsetInBytes] index of the region is
-   * not specified, it defaults to zero (the first byte in the byte buffer).
-   * If the length is not specified, it defaults to null, which indicates that
-   * the view extends to the end of the byte buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   */
-  external factory Uint8ClampedList.view(ByteBuffer buffer,
-                                         [int offsetInBytes = 0, int length]);
-
-  static const int BYTES_PER_ELEMENT = 1;
-}
-
-
-/**
- * A fixed-length list of 16-bit signed integers that is viewable as a
- * [TypedData]. For long lists, this implementation can be considerably
- * more space- and time-efficient than the default [List] implementation.
- */
-abstract class Int16List implements List<int>, TypedData {
-  /**
-   * Creates an [Int16List] of the specified length (in elements), all of
-   * whose elements are initially zero.
-   */
-  external factory Int16List(int length);
-
-  /**
-   * Creates an [Int16List] _view_ of the specified region in the specified
-   * byte buffer. Changes in the [Int16List] will be visible in the byte
-   * buffer and vice versa. If the [offsetInBytes] index of the region is not
-   * specified, it defaults to zero (the first byte in the byte buffer).
-   * If the length is not specified, it defaults to null, which indicates
-   * that the view extends to the end of the byte buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   *
-   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
-   * BYTES_PER_ELEMENT.
-   */
-  external factory Int16List.view(ByteBuffer buffer,
-                                  [int offsetInBytes = 0, int length]);
-
-  static const int BYTES_PER_ELEMENT = 2;
-}
-
-
-/**
- * A fixed-length list of 16-bit unsigned integers that is viewable as a
- * [TypedData]. For long lists, this implementation can be considerably
- * more space- and time-efficient than the default [List] implementation.
- */
-abstract class Uint16List implements List<int>, TypedData {
-  /**
-   * Creates a [Uint16List] of the specified length (in elements), all
-   * of whose elements are initially zero.
-   */
-  external factory Uint16List(int length);
-
-  /**
-   * Creates a [Uint16List] _view_ of the specified region in
-   * the specified byte buffer. Changes in the [Uint16List] will be
-   * visible in the byte buffer and vice versa. If the [offsetInBytes] index
-   * of the region is not specified, it defaults to zero (the first byte in
-   * the byte buffer). If the length is not specified, it defaults to null,
-   * which indicates that the view extends to the end of the byte buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   *
-   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
-   * BYTES_PER_ELEMENT.
-   */
-  external factory Uint16List.view(ByteBuffer buffer,
-                                   [int offsetInBytes = 0, int length]);
-
-  static const int BYTES_PER_ELEMENT = 2;
-}
-
-
-/**
- * A fixed-length list of 32-bit signed integers that is viewable as a
- * [TypedData]. For long lists, this implementation can be considerably
- * more space- and time-efficient than the default [List] implementation.
- */
-abstract class Int32List implements List<int>, TypedData {
-  /**
-   * Creates an [Int32List] of the specified length (in elements), all of
-   * whose elements are initially zero.
-   */
-  external factory Int32List(int length);
-
-  /**
-   * Creates an [Int32List] _view_ of the specified region in the specified
-   * byte buffer. Changes in the [Int32List] will be visible in the byte
-   * buffer and vice versa. If the [offsetInBytes] index of the region is not
-   * specified, it defaults to zero (the first byte in the byte buffer).
-   * If the length is not specified, it defaults to null, which indicates
-   * that the view extends to the end of the byte buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   *
-   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
-   * BYTES_PER_ELEMENT.
-   */
-  external factory Int32List.view(ByteBuffer buffer,
-                                  [int offsetInBytes = 0, int length]);
-
-  static const int BYTES_PER_ELEMENT = 4;
-}
-
-
-/**
- * A fixed-length list of 32-bit unsigned integers that is viewable as a
- * [TypedData]. For long lists, this implementation can be considerably
- * more space- and time-efficient than the default [List] implementation.
- */
-abstract class Uint32List implements List<int>, TypedData {
-  /**
-   * Creates a [Uint32List] of the specified length (in elements), all
-   * of whose elements are initially zero.
-   */
-  external factory Uint32List(int length);
-
-  /**
-   * Creates a [Uint32List] _view_ of the specified region in
-   * the specified byte buffer. Changes in the [Uint32] will be
-   * visible in the byte buffer and vice versa. If the [offsetInBytes] index
-   * of the region is not specified, it defaults to zero (the first byte in
-   * the byte buffer). If the length is not specified, it defaults to null,
-   * which indicates that the view extends to the end of the byte buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   *
-   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
-   * BYTES_PER_ELEMENT.
-   */
-  external factory Uint32List.view(ByteBuffer buffer,
-                                   [int offsetInBytes = 0, int length]);
-
-  static const int BYTES_PER_ELEMENT = 4;
-}
-
-
-/**
- * A fixed-length list of 64-bit signed integers that is viewable as a
- * [TypedData]. For long lists, this implementation can be considerably
- * more space- and time-efficient than the default [List] implementation.
- */
-abstract class Int64List implements List<int>, TypedData {
-  /**
-   * Creates an [Int64List] of the specified length (in elements), all of
-   * whose elements are initially zero.
-   */
-  external factory Int64List(int length);
-
-  /**
-   * Creates an [Int64List] _view_ of the specified region in the specified
-   * byte buffer. Changes in the [Int64List] will be visible in the byte buffer
-   * and vice versa. If the [offsetInBytes] index of the region is not
-   * specified, it defaults to zero (the first byte in the byte buffer).
-   * If the length is not specified, it defaults to null, which indicates that
-   * the view extends to the end of the byte buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   *
-   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
-   * BYTES_PER_ELEMENT.
-   */
-  external factory Int64List.view(ByteBuffer buffer,
-                                  [int offsetInBytes = 0, int length]);
-
-  static const int BYTES_PER_ELEMENT = 8;
-}
-
-
-/**
- * A fixed-length list of 64-bit unsigned integers that is viewable as a
- * [TypedData]. For long lists, this implementation can be considerably
- * more space- and time-efficient than the default [List] implementation.
- */
-abstract class Uint64List implements List<int>, TypedData {
-  /**
-   * Creates a [Uint64List] of the specified length (in elements), all
-   * of whose elements are initially zero.
-   */
-  external factory Uint64List(int length);
-
-  /**
-   * Creates an [Uint64List] _view_ of the specified region in
-   * the specified byte buffer. Changes in the [Uint64List] will be
-   * visible in the byte buffer and vice versa. If the [offsetInBytes]
-   * index of the region is not specified, it defaults to zero (the first
-   * byte in the byte buffer). If the length is not specified, it defaults
-   * to null, which indicates that the view extends to the end of the byte
-   * buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   *
-   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
-   * BYTES_PER_ELEMENT.
-   */
-  external factory Uint64List.view(ByteBuffer buffer,
-                                   [int offsetInBytes = 0, int length]);
-
-  static const int BYTES_PER_ELEMENT = 8;
-}
-
-
-/**
- * A fixed-length list of IEEE 754 single-precision binary floating-point
- * numbers  that is viewable as a [TypedData]. For long lists, this
- * implementation can be considerably more space- and time-efficient than
- * the default [List] implementation.
- */
-abstract class Float32List implements List<double>, TypedData {
-  /**
-   * Creates a [Float32List] of the specified length (in elements), all of
-   * whose elements are initially zero.
-   */
-  external factory Float32List(int length);
-
-  /**
-   * Creates a [Float32List] _view_ of the specified region in the specified
-   * byte buffer. Changes in the [Float32List] will be visible in the byte
-   * buffer and vice versa. If the [offsetInBytes] index of the region is not
-   * specified, it defaults to zero (the first byte in the byte buffer).
-   * If the length is not specified, it defaults to null, which indicates
-   * that the view extends to the end of the byte buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   *
-   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
-   * BYTES_PER_ELEMENT.
-   */
-  external factory Float32List.view(ByteBuffer buffer,
-                                    [int offsetInBytes = 0, int length]);
-
-  static const int BYTES_PER_ELEMENT = 4;
-}
-
-
-/**
- * A fixed-length list of IEEE 754 double-precision binary floating-point
- * numbers  that is viewable as a [TypedData]. For long lists, this
- * implementation can be considerably more space- and time-efficient than
- * the default [List] implementation.
- */
-abstract class Float64List implements List<double>, TypedData {
-  /**
-   * Creates a [Float64List] of the specified length (in elements), all of
-   * whose elements are initially zero.
-   */
-  external factory Float64List(int length);
-
-  /**
-   * Creates a [Float64List] _view_ of the specified region in the specified
-   * byte buffer. Changes in the [Float64List] will be visible in the byte
-   * buffer and vice versa. If the [offsetInBytes] index of the region is not
-   * specified, it defaults to zero (the first byte in the byte buffer).
-   * If the length is not specified, it defaults to null, which indicates
-   * that the view extends to the end of the byte buffer.
-   *
-   * Throws [RangeError] if [offsetInBytes] or [length] are negative, or
-   * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than
-   * the length of [buffer].
-   *
-   * Throws [ArgumentError] if [offsetInBytes] is not a multiple of
-   * BYTES_PER_ELEMENT.
-   */
-  external factory Float64List.view(ByteBuffer buffer,
-                                    [int offsetInBytes = 0, int length]);
-
-  static const int BYTES_PER_ELEMENT = 8;
-}
diff --git a/sdk/lib/typeddata/typeddata_sources.gypi b/sdk/lib/typeddata/typeddata_sources.gypi
index 7961185..92ce89d 100644
--- a/sdk/lib/typeddata/typeddata_sources.gypi
+++ b/sdk/lib/typeddata/typeddata_sources.gypi
@@ -5,7 +5,6 @@
 {
   'sources': [
     'typeddata.dart',
-    # The above file needs to be first as it lists the parts below.
-    'typeddata_base.dart',
+    # The above file needs to be first if additional parts are added to the lib.
   ],
 }
diff --git a/sdk/lib/uri/uri.dart b/sdk/lib/uri/uri.dart
index f3876f6..640ce3d 100644
--- a/sdk/lib/uri/uri.dart
+++ b/sdk/lib/uri/uri.dart
@@ -7,6 +7,259 @@
 import 'dart:math';
 import 'dart:utf';
 
-part 'uri_base.dart';
 part 'encode_decode.dart';
 part 'helpers.dart';
+
+/**
+ * A parsed URI, inspired by Closure's [URI][] class. Implements [RFC-3986][].
+ * [uri]: http://closure-library.googlecode.com/svn/docs/class_goog_Uri.html
+ * [RFC-3986]: http://tools.ietf.org/html/rfc3986#section-4.3)
+ */
+class Uri {
+  final String scheme;
+  final String userInfo;
+  final String domain;
+  final int port;
+  final String path;
+  final String query;
+  final String fragment;
+
+  /**
+   * Deprecated. Please use [parse] instead.
+   */
+  Uri.fromString(String uri) : this._fromMatch(_splitRe.firstMatch(uri));
+
+  static Uri parse(String uri) => new Uri._fromMatch(_splitRe.firstMatch(uri));
+
+  Uri._fromMatch(Match m) :
+    this.fromComponents(scheme: _emptyIfNull(m[_COMPONENT_SCHEME]),
+                        userInfo: _emptyIfNull(m[_COMPONENT_USER_INFO]),
+                        domain: _emptyIfNull(m[_COMPONENT_DOMAIN]),
+                        port: _parseIntOrZero(m[_COMPONENT_PORT]),
+                        path: _emptyIfNull(m[_COMPONENT_PATH]),
+                        query: _emptyIfNull(m[_COMPONENT_QUERY_DATA]),
+                        fragment: _emptyIfNull(m[_COMPONENT_FRAGMENT]));
+
+  const Uri.fromComponents({this.scheme: "",
+                            this.userInfo: "",
+                            this.domain: "",
+                            this.port: 0,
+                            this.path: "",
+                            this.query: "",
+                            this.fragment: ""});
+
+  Uri(String uri) : this.fromString(uri);
+
+  static String _emptyIfNull(String val) => val != null ? val : '';
+
+  static int _parseIntOrZero(String val) {
+    if (val != null && val != '') {
+      return int.parse(val);
+    } else {
+      return 0;
+    }
+  }
+
+  // NOTE: This code was ported from: closure-library/closure/goog/uri/utils.js
+  static final RegExp _splitRe = new RegExp(
+      '^'
+      '(?:'
+        '([^:/?#.]+)'                   // scheme - ignore special characters
+                                        // used by other URL parts such as :,
+                                        // ?, /, #, and .
+      ':)?'
+      '(?://'
+        '(?:([^/?#]*)@)?'               // userInfo
+        '([\\w\\d\\-\\u0100-\\uffff.%]*)'
+                                        // domain - restrict to letters,
+                                        // digits, dashes, dots, percent
+                                        // escapes, and unicode characters.
+        '(?::([0-9]+))?'                // port
+      ')?'
+      '([^?#]+)?'                       // path
+      '(?:\\?([^#]*))?'                 // query
+      '(?:#(.*))?'                      // fragment
+      '\$');
+
+  static const _COMPONENT_SCHEME = 1;
+  static const _COMPONENT_USER_INFO = 2;
+  static const _COMPONENT_DOMAIN = 3;
+  static const _COMPONENT_PORT = 4;
+  static const _COMPONENT_PATH = 5;
+  static const _COMPONENT_QUERY_DATA = 6;
+  static const _COMPONENT_FRAGMENT = 7;
+
+  /**
+   * Returns `true` if the URI is absolute.
+   */
+  bool get isAbsolute {
+    if ("" == scheme) return false;
+    if ("" != fragment) return false;
+    return true;
+
+    /* absolute-URI  = scheme ":" hier-part [ "?" query ]
+     * hier-part   = "//" authority path-abempty
+     *             / path-absolute
+     *             / path-rootless
+     *             / path-empty
+     *
+     * path          = path-abempty    ; begins with "/" or is empty
+     *               / path-absolute   ; begins with "/" but not "//"
+     *               / path-noscheme   ; begins with a non-colon segment
+     *               / path-rootless   ; begins with a segment
+     *               / path-empty      ; zero characters
+     *
+     * path-abempty  = *( "/" segment )
+     * path-absolute = "/" [ segment-nz *( "/" segment ) ]
+     * path-noscheme = segment-nz-nc *( "/" segment )
+     * path-rootless = segment-nz *( "/" segment )
+     * path-empty    = 0<pchar>
+     * segment       = *pchar
+     * segment-nz    = 1*pchar
+     * segment-nz-nc = 1*( unreserved / pct-encoded / sub-delims / "@" )
+     *               ; non-zero-length segment without any colon ":"
+     *
+     * pchar         = unreserved / pct-encoded / sub-delims / ":" / "@"
+     */
+  }
+
+  Uri resolve(String uri) {
+    return resolveUri(Uri.parse(uri));
+  }
+
+  Uri resolveUri(Uri reference) {
+    // From RFC 3986.
+    String targetScheme;
+    String targetUserInfo;
+    String targetDomain;
+    int targetPort;
+    String targetPath;
+    String targetQuery;
+    if (reference.scheme != "") {
+      targetScheme = reference.scheme;
+      targetUserInfo = reference.userInfo;
+      targetDomain = reference.domain;
+      targetPort = reference.port;
+      targetPath = removeDotSegments(reference.path);
+      targetQuery = reference.query;
+    } else {
+      if (reference.hasAuthority) {
+        targetUserInfo = reference.userInfo;
+        targetDomain = reference.domain;
+        targetPort = reference.port;
+        targetPath = removeDotSegments(reference.path);
+        targetQuery = reference.query;
+      } else {
+        if (reference.path == "") {
+          targetPath = this.path;
+          if (reference.query != "") {
+            targetQuery = reference.query;
+          } else {
+            targetQuery = this.query;
+          }
+        } else {
+          if (reference.path.startsWith("/")) {
+            targetPath = removeDotSegments(reference.path);
+          } else {
+            targetPath = removeDotSegments(merge(this.path, reference.path));
+          }
+          targetQuery = reference.query;
+        }
+        targetUserInfo = this.userInfo;
+        targetDomain = this.domain;
+        targetPort = this.port;
+      }
+      targetScheme = this.scheme;
+    }
+    return new Uri.fromComponents(scheme: targetScheme,
+                                  userInfo: targetUserInfo,
+                                  domain: targetDomain,
+                                  port: targetPort,
+                                  path: targetPath,
+                                  query: targetQuery,
+                                  fragment: reference.fragment);
+  }
+
+  bool get hasAuthority {
+    return (userInfo != "") || (domain != "") || (port != 0);
+  }
+
+  /**
+   * For http/https schemes returns URI's [origin][] - scheme://domain:port.
+   * For all other schemes throws ArgumentError.
+   * [origin]: http://www.w3.org/TR/2011/WD-html5-20110405/origin-0.html#origin
+   */
+  String get origin {
+    if (scheme == "") {
+      // TODO(aprelev@gmail.com): Use StateException instead
+      throw new ArgumentError("Cannot use origin without a scheme");
+    }
+    if (scheme != "http" && scheme != "https") {
+      // TODO(aprelev@gmail.com): Use StateException instead
+      throw new ArgumentError(
+        "origin is applicable to http/https schemes only. Not \'$scheme\'");
+    }
+    StringBuffer sb = new StringBuffer();
+    sb.write(scheme);
+    sb.write(":");
+    if (domain == null || domain == "") {
+      // TODO(aprelev@gmail.com): Use StateException instead
+      throw new ArgumentError("Cannot use origin without a domain");
+    }
+
+    sb.write("//");
+    sb.write(domain);
+    if (port != 0) {
+      sb.write(":");
+      sb.write(port);
+    }
+    return sb.toString();
+  }
+
+  String toString() {
+    StringBuffer sb = new StringBuffer();
+    _addIfNonEmpty(sb, scheme, scheme, ':');
+    if (hasAuthority || (scheme == "file")) {
+      sb.write("//");
+      _addIfNonEmpty(sb, userInfo, userInfo, "@");
+      sb.write(domain == null ? "null" : domain);
+      if (port != 0) {
+        sb.write(":");
+        sb.write(port.toString());
+      }
+    }
+    sb.write(path == null ? "null" : path);
+    _addIfNonEmpty(sb, query, "?", query);
+    _addIfNonEmpty(sb, fragment, "#", fragment);
+    return sb.toString();
+  }
+
+  bool operator==(other) {
+    if (other is! Uri) return false;
+    Uri uri = other;
+    return scheme == uri.scheme &&
+        userInfo == uri.userInfo &&
+        domain == uri.domain &&
+        port == uri.port &&
+        path == uri.path &&
+        query == uri.query &&
+        fragment == uri.fragment;
+  }
+
+  int get hashCode {
+    int combine(part, current) {
+      // The sum is truncated to 30 bits to make sure it fits into a Smi.
+      return (current * 31 + part.hashCode) & 0x3FFFFFFF;
+    }
+    return combine(scheme, combine(userInfo, combine(domain, combine(port,
+        combine(path, combine(query, combine(fragment, 1)))))));
+  }
+
+  static void _addIfNonEmpty(StringBuffer sb, String test,
+                             String first, String second) {
+    if ("" != test) {
+      sb.write(first == null ? "null" : first);
+      sb.write(second == null ? "null" : second);
+    }
+  }
+}
diff --git a/sdk/lib/uri/uri_base.dart b/sdk/lib/uri/uri_base.dart
deleted file mode 100644
index 9f228d4..0000000
--- a/sdk/lib/uri/uri_base.dart
+++ /dev/null
@@ -1,259 +0,0 @@
-// Copyright (c) 2012, 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 dart.uri;
-
-/**
- * A parsed URI, inspired by Closure's [URI][] class. Implements [RFC-3986][].
- * [uri]: http://closure-library.googlecode.com/svn/docs/class_goog_Uri.html
- * [RFC-3986]: http://tools.ietf.org/html/rfc3986#section-4.3)
- */
-class Uri {
-  final String scheme;
-  final String userInfo;
-  final String domain;
-  final int port;
-  final String path;
-  final String query;
-  final String fragment;
-
-  /**
-   * Deprecated. Please use [parse] instead.
-   */
-  Uri.fromString(String uri) : this._fromMatch(_splitRe.firstMatch(uri));
-
-  static Uri parse(String uri) => new Uri._fromMatch(_splitRe.firstMatch(uri));
-
-  Uri._fromMatch(Match m) :
-    this.fromComponents(scheme: _emptyIfNull(m[_COMPONENT_SCHEME]),
-                        userInfo: _emptyIfNull(m[_COMPONENT_USER_INFO]),
-                        domain: _emptyIfNull(m[_COMPONENT_DOMAIN]),
-                        port: _parseIntOrZero(m[_COMPONENT_PORT]),
-                        path: _emptyIfNull(m[_COMPONENT_PATH]),
-                        query: _emptyIfNull(m[_COMPONENT_QUERY_DATA]),
-                        fragment: _emptyIfNull(m[_COMPONENT_FRAGMENT]));
-
-  const Uri.fromComponents({this.scheme: "",
-                            this.userInfo: "",
-                            this.domain: "",
-                            this.port: 0,
-                            this.path: "",
-                            this.query: "",
-                            this.fragment: ""});
-
-  Uri(String uri) : this.fromString(uri);
-
-  static String _emptyIfNull(String val) => val != null ? val : '';
-
-  static int _parseIntOrZero(String val) {
-    if (val != null && val != '') {
-      return int.parse(val);
-    } else {
-      return 0;
-    }
-  }
-
-  // NOTE: This code was ported from: closure-library/closure/goog/uri/utils.js
-  static final RegExp _splitRe = new RegExp(
-      '^'
-      '(?:'
-        '([^:/?#.]+)'                   // scheme - ignore special characters
-                                        // used by other URL parts such as :,
-                                        // ?, /, #, and .
-      ':)?'
-      '(?://'
-        '(?:([^/?#]*)@)?'               // userInfo
-        '([\\w\\d\\-\\u0100-\\uffff.%]*)'
-                                        // domain - restrict to letters,
-                                        // digits, dashes, dots, percent
-                                        // escapes, and unicode characters.
-        '(?::([0-9]+))?'                // port
-      ')?'
-      '([^?#]+)?'                       // path
-      '(?:\\?([^#]*))?'                 // query
-      '(?:#(.*))?'                      // fragment
-      '\$');
-
-  static const _COMPONENT_SCHEME = 1;
-  static const _COMPONENT_USER_INFO = 2;
-  static const _COMPONENT_DOMAIN = 3;
-  static const _COMPONENT_PORT = 4;
-  static const _COMPONENT_PATH = 5;
-  static const _COMPONENT_QUERY_DATA = 6;
-  static const _COMPONENT_FRAGMENT = 7;
-
-  /**
-   * Returns `true` if the URI is absolute.
-   */
-  bool get isAbsolute {
-    if ("" == scheme) return false;
-    if ("" != fragment) return false;
-    return true;
-
-    /* absolute-URI  = scheme ":" hier-part [ "?" query ]
-     * hier-part   = "//" authority path-abempty
-     *             / path-absolute
-     *             / path-rootless
-     *             / path-empty
-     *
-     * path          = path-abempty    ; begins with "/" or is empty
-     *               / path-absolute   ; begins with "/" but not "//"
-     *               / path-noscheme   ; begins with a non-colon segment
-     *               / path-rootless   ; begins with a segment
-     *               / path-empty      ; zero characters
-     *
-     * path-abempty  = *( "/" segment )
-     * path-absolute = "/" [ segment-nz *( "/" segment ) ]
-     * path-noscheme = segment-nz-nc *( "/" segment )
-     * path-rootless = segment-nz *( "/" segment )
-     * path-empty    = 0<pchar>
-     * segment       = *pchar
-     * segment-nz    = 1*pchar
-     * segment-nz-nc = 1*( unreserved / pct-encoded / sub-delims / "@" )
-     *               ; non-zero-length segment without any colon ":"
-     *
-     * pchar         = unreserved / pct-encoded / sub-delims / ":" / "@"
-     */
-  }
-
-  Uri resolve(String uri) {
-    return resolveUri(Uri.parse(uri));
-  }
-
-  Uri resolveUri(Uri reference) {
-    // From RFC 3986.
-    String targetScheme;
-    String targetUserInfo;
-    String targetDomain;
-    int targetPort;
-    String targetPath;
-    String targetQuery;
-    if (reference.scheme != "") {
-      targetScheme = reference.scheme;
-      targetUserInfo = reference.userInfo;
-      targetDomain = reference.domain;
-      targetPort = reference.port;
-      targetPath = removeDotSegments(reference.path);
-      targetQuery = reference.query;
-    } else {
-      if (reference.hasAuthority) {
-        targetUserInfo = reference.userInfo;
-        targetDomain = reference.domain;
-        targetPort = reference.port;
-        targetPath = removeDotSegments(reference.path);
-        targetQuery = reference.query;
-      } else {
-        if (reference.path == "") {
-          targetPath = this.path;
-          if (reference.query != "") {
-            targetQuery = reference.query;
-          } else {
-            targetQuery = this.query;
-          }
-        } else {
-          if (reference.path.startsWith("/")) {
-            targetPath = removeDotSegments(reference.path);
-          } else {
-            targetPath = removeDotSegments(merge(this.path, reference.path));
-          }
-          targetQuery = reference.query;
-        }
-        targetUserInfo = this.userInfo;
-        targetDomain = this.domain;
-        targetPort = this.port;
-      }
-      targetScheme = this.scheme;
-    }
-    return new Uri.fromComponents(scheme: targetScheme,
-                                  userInfo: targetUserInfo,
-                                  domain: targetDomain,
-                                  port: targetPort,
-                                  path: targetPath,
-                                  query: targetQuery,
-                                  fragment: reference.fragment);
-  }
-
-  bool get hasAuthority {
-    return (userInfo != "") || (domain != "") || (port != 0);
-  }
-
-  /**
-   * For http/https schemes returns URI's [origin][] - scheme://domain:port.
-   * For all other schemes throws ArgumentError.
-   * [origin]: http://www.w3.org/TR/2011/WD-html5-20110405/origin-0.html#origin
-   */
-  String get origin {
-    if (scheme == "") {
-      // TODO(aprelev@gmail.com): Use StateException instead
-      throw new ArgumentError("Cannot use origin without a scheme");
-    }
-    if (scheme != "http" && scheme != "https") {
-      // TODO(aprelev@gmail.com): Use StateException instead
-      throw new ArgumentError(
-        "origin is applicable to http/https schemes only. Not \'$scheme\'");
-    }
-    StringBuffer sb = new StringBuffer();
-    sb.write(scheme);
-    sb.write(":");
-    if (domain == null || domain == "") {
-      // TODO(aprelev@gmail.com): Use StateException instead
-      throw new ArgumentError("Cannot use origin without a domain");
-    }
-
-    sb.write("//");
-    sb.write(domain);
-    if (port != 0) {
-      sb.write(":");
-      sb.write(port);
-    }
-    return sb.toString();
-  }
-
-  String toString() {
-    StringBuffer sb = new StringBuffer();
-    _addIfNonEmpty(sb, scheme, scheme, ':');
-    if (hasAuthority || (scheme == "file")) {
-      sb.write("//");
-      _addIfNonEmpty(sb, userInfo, userInfo, "@");
-      sb.write(domain == null ? "null" : domain);
-      if (port != 0) {
-        sb.write(":");
-        sb.write(port.toString());
-      }
-    }
-    sb.write(path == null ? "null" : path);
-    _addIfNonEmpty(sb, query, "?", query);
-    _addIfNonEmpty(sb, fragment, "#", fragment);
-    return sb.toString();
-  }
-
-  bool operator==(other) {
-    if (other is! Uri) return false;
-    Uri uri = other;
-    return scheme == uri.scheme &&
-        userInfo == uri.userInfo &&
-        domain == uri.domain &&
-        port == uri.port &&
-        path == uri.path &&
-        query == uri.query &&
-        fragment == uri.fragment;
-  }
-
-  int get hashCode {
-    int combine(part, current) {
-      // The sum is truncated to 30 bits to make sure it fits into a Smi.
-      return (current * 31 + part.hashCode) & 0x3FFFFFFF;
-    }
-    return combine(scheme, combine(userInfo, combine(domain, combine(port,
-        combine(path, combine(query, combine(fragment, 1)))))));
-  }
-
-  static void _addIfNonEmpty(StringBuffer sb, String test,
-                             String first, String second) {
-    if ("" != test) {
-      sb.write(first == null ? "null" : first);
-      sb.write(second == null ? "null" : second);
-    }
-  }
-}
diff --git a/sdk/lib/uri/uri_sources.gypi b/sdk/lib/uri/uri_sources.gypi
index b777678..09f54fc 100644
--- a/sdk/lib/uri/uri_sources.gypi
+++ b/sdk/lib/uri/uri_sources.gypi
@@ -7,7 +7,6 @@
   'sources': [
     'uri.dart',
     # The above file needs to be first as it lists the parts below.
-    'uri_base.dart',
     'helpers.dart',
     'encode_decode.dart',
   ],
diff --git a/sdk/lib/utf/utf.dart b/sdk/lib/utf/utf.dart
index abc3f84..2031e62 100644
--- a/sdk/lib/utf/utf.dart
+++ b/sdk/lib/utf/utf.dart
@@ -4,8 +4,259 @@
 
 library dart.utf;
 import "dart:async";
-part "utf_core.dart";
 part "utf_stream.dart";
 part "utf8.dart";
 part "utf16.dart";
 part "utf32.dart";
+
+// TODO(jmesserly): would be nice to have this on String (dartbug.com/6501).
+/**
+ * Provide a list of Unicode codepoints for a given string.
+ */
+List<int> stringToCodepoints(String str) {
+  // Note: str.codeUnits gives us 16-bit code units on all Dart implementations.
+  // So we need to convert.
+  return _utf16CodeUnitsToCodepoints(str.codeUnits);
+}
+
+/**
+ * Generate a string from the provided Unicode codepoints.
+ */
+String codepointsToString(List<int> codepoints) {
+  return new String.fromCharCodes(codepoints);
+}
+
+/**
+ * Invalid codepoints or encodings may be substituted with the value U+fffd.
+ */
+const int UNICODE_REPLACEMENT_CHARACTER_CODEPOINT = 0xfffd;
+const int UNICODE_BOM = 0xfeff;
+const int UNICODE_UTF_BOM_LO = 0xff;
+const int UNICODE_UTF_BOM_HI = 0xfe;
+
+const int UNICODE_BYTE_ZERO_MASK = 0xff;
+const int UNICODE_BYTE_ONE_MASK = 0xff00;
+const int UNICODE_VALID_RANGE_MAX = 0x10ffff;
+const int UNICODE_PLANE_ONE_MAX = 0xffff;
+const int UNICODE_UTF16_RESERVED_LO = 0xd800;
+const int UNICODE_UTF16_RESERVED_HI = 0xdfff;
+const int UNICODE_UTF16_OFFSET = 0x10000;
+const int UNICODE_UTF16_SURROGATE_UNIT_0_BASE = 0xd800;
+const int UNICODE_UTF16_SURROGATE_UNIT_1_BASE = 0xdc00;
+const int UNICODE_UTF16_HI_MASK = 0xffc00;
+const int UNICODE_UTF16_LO_MASK = 0x3ff;
+
+/**
+ * Encode code points as UTF16 code units.
+ */
+List<int> _codepointsToUtf16CodeUnits(
+    List<int> codepoints,
+    [int offset = 0,
+     int length,
+     int replacementCodepoint = UNICODE_REPLACEMENT_CHARACTER_CODEPOINT]) {
+
+  _ListRange listRange = new _ListRange(codepoints, offset, length);
+  int encodedLength = 0;
+  for (int value in listRange) {
+    if ((value >= 0 && value < UNICODE_UTF16_RESERVED_LO) ||
+        (value > UNICODE_UTF16_RESERVED_HI && value <= UNICODE_PLANE_ONE_MAX)) {
+      encodedLength++;
+    } else if (value > UNICODE_PLANE_ONE_MAX &&
+        value <= UNICODE_VALID_RANGE_MAX) {
+      encodedLength += 2;
+    } else {
+      encodedLength++;
+    }
+  }
+
+  List<int> codeUnitsBuffer = new List<int>(encodedLength);
+  int j = 0;
+  for (int value in listRange) {
+    if ((value >= 0 && value < UNICODE_UTF16_RESERVED_LO) ||
+        (value > UNICODE_UTF16_RESERVED_HI && value <= UNICODE_PLANE_ONE_MAX)) {
+      codeUnitsBuffer[j++] = value;
+    } else if (value > UNICODE_PLANE_ONE_MAX &&
+        value <= UNICODE_VALID_RANGE_MAX) {
+      int base = value - UNICODE_UTF16_OFFSET;
+      codeUnitsBuffer[j++] = UNICODE_UTF16_SURROGATE_UNIT_0_BASE +
+          ((base & UNICODE_UTF16_HI_MASK) >> 10);
+      codeUnitsBuffer[j++] = UNICODE_UTF16_SURROGATE_UNIT_1_BASE +
+          (base & UNICODE_UTF16_LO_MASK);
+    } else if (replacementCodepoint != null) {
+      codeUnitsBuffer[j++] = replacementCodepoint;
+    } else {
+      throw new ArgumentError("Invalid encoding");
+    }
+  }
+  return codeUnitsBuffer;
+}
+
+/**
+ * Decodes the utf16 codeunits to codepoints.
+ */
+List<int> _utf16CodeUnitsToCodepoints(
+    List<int> utf16CodeUnits, [int offset = 0, int length,
+    int replacementCodepoint = UNICODE_REPLACEMENT_CHARACTER_CODEPOINT]) {
+  _ListRangeIterator source =
+      (new _ListRange(utf16CodeUnits, offset, length)).iterator;
+  Utf16CodeUnitDecoder decoder = new Utf16CodeUnitDecoder
+      .fromListRangeIterator(source, replacementCodepoint);
+  List<int> codepoints = new List<int>(source.remaining);
+  int i = 0;
+  while (decoder.moveNext()) {
+    codepoints[i++] = decoder.current;
+  }
+  if (i == codepoints.length) {
+    return codepoints;
+  } else {
+    List<int> codepointTrunc = new List<int>(i);
+    codepointTrunc.setRange(0, i, codepoints);
+    return codepointTrunc;
+  }
+}
+
+/**
+ * An Iterator<int> of codepoints built on an Iterator of UTF-16 code units.
+ * The parameters can override the default Unicode replacement character. Set
+ * the replacementCharacter to null to throw an ArgumentError
+ * rather than replace the bad value.
+ */
+class Utf16CodeUnitDecoder implements Iterator<int> {
+  final _ListRangeIterator utf16CodeUnitIterator;
+  final int replacementCodepoint;
+  int _current = null;
+
+  Utf16CodeUnitDecoder(List<int> utf16CodeUnits, [int offset = 0, int length,
+      int this.replacementCodepoint =
+      UNICODE_REPLACEMENT_CHARACTER_CODEPOINT]) :
+      utf16CodeUnitIterator =
+          (new _ListRange(utf16CodeUnits, offset, length)).iterator;
+
+  Utf16CodeUnitDecoder.fromListRangeIterator(
+      _ListRangeIterator this.utf16CodeUnitIterator,
+      int this.replacementCodepoint);
+
+  Iterator<int> get iterator => this;
+
+  int get current => _current;
+
+  bool moveNext() {
+    _current = null;
+    if (!utf16CodeUnitIterator.moveNext()) return false;
+
+    int value = utf16CodeUnitIterator.current;
+    if (value < 0) {
+      if (replacementCodepoint != null) {
+        _current = replacementCodepoint;
+      } else {
+        throw new ArgumentError(
+            "Invalid UTF16 at ${utf16CodeUnitIterator.position}");
+      }
+    } else if (value < UNICODE_UTF16_RESERVED_LO ||
+        (value > UNICODE_UTF16_RESERVED_HI && value <= UNICODE_PLANE_ONE_MAX)) {
+      // transfer directly
+      _current = value;
+    } else if (value < UNICODE_UTF16_SURROGATE_UNIT_1_BASE &&
+        utf16CodeUnitIterator.moveNext()) {
+      // merge surrogate pair
+      int nextValue = utf16CodeUnitIterator.current;
+      if (nextValue >= UNICODE_UTF16_SURROGATE_UNIT_1_BASE &&
+          nextValue <= UNICODE_UTF16_RESERVED_HI) {
+        value = (value - UNICODE_UTF16_SURROGATE_UNIT_0_BASE) << 10;
+        value += UNICODE_UTF16_OFFSET +
+            (nextValue - UNICODE_UTF16_SURROGATE_UNIT_1_BASE);
+        _current = value;
+      } else {
+        if (nextValue >= UNICODE_UTF16_SURROGATE_UNIT_0_BASE &&
+           nextValue < UNICODE_UTF16_SURROGATE_UNIT_1_BASE) {
+          utf16CodeUnitIterator.backup();
+        }
+        if (replacementCodepoint != null) {
+          _current = replacementCodepoint;
+        } else {
+          throw new ArgumentError(
+              "Invalid UTF16 at ${utf16CodeUnitIterator.position}");
+        }
+      }
+    } else if (replacementCodepoint != null) {
+      _current = replacementCodepoint;
+    } else {
+      throw new ArgumentError(
+          "Invalid UTF16 at ${utf16CodeUnitIterator.position}");
+    }
+    return true;
+  }
+}
+
+/**
+ * _ListRange in an internal type used to create a lightweight Interable on a
+ * range within a source list. DO NOT MODIFY the underlying list while
+ * iterating over it. The results of doing so are undefined.
+ */
+// TODO(floitsch): Consider removing the extend and switch to implements since
+// that's cheaper to allocate.
+class _ListRange extends Iterable {
+  final List _source;
+  final int _offset;
+  final int _length;
+
+  _ListRange(source, [offset = 0, length]) :
+      this._source = source,
+      this._offset = offset,
+      this._length = (length == null ? source.length - offset : length) {
+    if (_offset < 0 || _offset > _source.length) {
+      throw new RangeError.value(_offset);
+    }
+    if (_length != null && (_length < 0)) {
+      throw new RangeError.value(_length);
+    }
+    if (_length + _offset > _source.length) {
+      throw new RangeError.value(_length + _offset);
+    }
+  }
+
+  _ListRangeIterator get iterator =>
+      new _ListRangeIteratorImpl(_source, _offset, _offset + _length);
+
+  int get length => _length;
+}
+
+/**
+ * The _ListRangeIterator provides more capabilities than a standard iterator,
+ * including the ability to get the current position, count remaining items,
+ * and move forward/backward within the iterator.
+ */
+abstract class _ListRangeIterator implements Iterator<int> {
+  bool moveNext();
+  int get current;
+  int get position;
+  void backup([by]);
+  int get remaining;
+  void skip([count]);
+}
+
+class _ListRangeIteratorImpl implements _ListRangeIterator {
+  final List<int> _source;
+  int _offset;
+  final int _end;
+
+  _ListRangeIteratorImpl(this._source, int offset, this._end)
+      : _offset = offset - 1;
+
+  int get current => _source[_offset];
+
+  bool moveNext() => ++_offset < _end;
+
+  int get position => _offset;
+
+  void backup([int by = 1]) {
+    _offset -= by;
+  }
+
+  int get remaining => _end - _offset - 1;
+
+  void skip([int count = 1]) {
+    _offset += count;
+  }
+}
+
diff --git a/sdk/lib/utf/utf_core.dart b/sdk/lib/utf/utf_core.dart
deleted file mode 100644
index 30ad2dc..0000000
--- a/sdk/lib/utf/utf_core.dart
+++ /dev/null
@@ -1,257 +0,0 @@
-// Copyright (c) 2012, 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 dart.utf;
-
-// TODO(jmesserly): would be nice to have this on String (dartbug.com/6501).
-/**
- * Provide a list of Unicode codepoints for a given string.
- */
-List<int> stringToCodepoints(String str) {
-  // Note: str.codeUnits gives us 16-bit code units on all Dart implementations.
-  // So we need to convert.
-  return _utf16CodeUnitsToCodepoints(str.codeUnits);
-}
-
-/**
- * Generate a string from the provided Unicode codepoints.
- */
-String codepointsToString(List<int> codepoints) {
-  return new String.fromCharCodes(codepoints);
-}
-
-/**
- * Invalid codepoints or encodings may be substituted with the value U+fffd.
- */
-const int UNICODE_REPLACEMENT_CHARACTER_CODEPOINT = 0xfffd;
-const int UNICODE_BOM = 0xfeff;
-const int UNICODE_UTF_BOM_LO = 0xff;
-const int UNICODE_UTF_BOM_HI = 0xfe;
-
-const int UNICODE_BYTE_ZERO_MASK = 0xff;
-const int UNICODE_BYTE_ONE_MASK = 0xff00;
-const int UNICODE_VALID_RANGE_MAX = 0x10ffff;
-const int UNICODE_PLANE_ONE_MAX = 0xffff;
-const int UNICODE_UTF16_RESERVED_LO = 0xd800;
-const int UNICODE_UTF16_RESERVED_HI = 0xdfff;
-const int UNICODE_UTF16_OFFSET = 0x10000;
-const int UNICODE_UTF16_SURROGATE_UNIT_0_BASE = 0xd800;
-const int UNICODE_UTF16_SURROGATE_UNIT_1_BASE = 0xdc00;
-const int UNICODE_UTF16_HI_MASK = 0xffc00;
-const int UNICODE_UTF16_LO_MASK = 0x3ff;
-
-/**
- * Encode code points as UTF16 code units.
- */
-List<int> _codepointsToUtf16CodeUnits(
-    List<int> codepoints,
-    [int offset = 0,
-     int length,
-     int replacementCodepoint = UNICODE_REPLACEMENT_CHARACTER_CODEPOINT]) {
-
-  _ListRange listRange = new _ListRange(codepoints, offset, length);
-  int encodedLength = 0;
-  for (int value in listRange) {
-    if ((value >= 0 && value < UNICODE_UTF16_RESERVED_LO) ||
-        (value > UNICODE_UTF16_RESERVED_HI && value <= UNICODE_PLANE_ONE_MAX)) {
-      encodedLength++;
-    } else if (value > UNICODE_PLANE_ONE_MAX &&
-        value <= UNICODE_VALID_RANGE_MAX) {
-      encodedLength += 2;
-    } else {
-      encodedLength++;
-    }
-  }
-
-  List<int> codeUnitsBuffer = new List<int>(encodedLength);
-  int j = 0;
-  for (int value in listRange) {
-    if ((value >= 0 && value < UNICODE_UTF16_RESERVED_LO) ||
-        (value > UNICODE_UTF16_RESERVED_HI && value <= UNICODE_PLANE_ONE_MAX)) {
-      codeUnitsBuffer[j++] = value;
-    } else if (value > UNICODE_PLANE_ONE_MAX &&
-        value <= UNICODE_VALID_RANGE_MAX) {
-      int base = value - UNICODE_UTF16_OFFSET;
-      codeUnitsBuffer[j++] = UNICODE_UTF16_SURROGATE_UNIT_0_BASE +
-          ((base & UNICODE_UTF16_HI_MASK) >> 10);
-      codeUnitsBuffer[j++] = UNICODE_UTF16_SURROGATE_UNIT_1_BASE +
-          (base & UNICODE_UTF16_LO_MASK);
-    } else if (replacementCodepoint != null) {
-      codeUnitsBuffer[j++] = replacementCodepoint;
-    } else {
-      throw new ArgumentError("Invalid encoding");
-    }
-  }
-  return codeUnitsBuffer;
-}
-
-/**
- * Decodes the utf16 codeunits to codepoints.
- */
-List<int> _utf16CodeUnitsToCodepoints(
-    List<int> utf16CodeUnits, [int offset = 0, int length,
-    int replacementCodepoint = UNICODE_REPLACEMENT_CHARACTER_CODEPOINT]) {
-  _ListRangeIterator source =
-      (new _ListRange(utf16CodeUnits, offset, length)).iterator;
-  Utf16CodeUnitDecoder decoder = new Utf16CodeUnitDecoder
-      .fromListRangeIterator(source, replacementCodepoint);
-  List<int> codepoints = new List<int>(source.remaining);
-  int i = 0;
-  while (decoder.moveNext()) {
-    codepoints[i++] = decoder.current;
-  }
-  if (i == codepoints.length) {
-    return codepoints;
-  } else {
-    List<int> codepointTrunc = new List<int>(i);
-    codepointTrunc.setRange(0, i, codepoints);
-    return codepointTrunc;
-  }
-}
-
-/**
- * An Iterator<int> of codepoints built on an Iterator of UTF-16 code units.
- * The parameters can override the default Unicode replacement character. Set
- * the replacementCharacter to null to throw an ArgumentError
- * rather than replace the bad value.
- */
-class Utf16CodeUnitDecoder implements Iterator<int> {
-  final _ListRangeIterator utf16CodeUnitIterator;
-  final int replacementCodepoint;
-  int _current = null;
-
-  Utf16CodeUnitDecoder(List<int> utf16CodeUnits, [int offset = 0, int length,
-      int this.replacementCodepoint =
-      UNICODE_REPLACEMENT_CHARACTER_CODEPOINT]) :
-      utf16CodeUnitIterator =
-          (new _ListRange(utf16CodeUnits, offset, length)).iterator;
-
-  Utf16CodeUnitDecoder.fromListRangeIterator(
-      _ListRangeIterator this.utf16CodeUnitIterator,
-      int this.replacementCodepoint);
-
-  Iterator<int> get iterator => this;
-
-  int get current => _current;
-
-  bool moveNext() {
-    _current = null;
-    if (!utf16CodeUnitIterator.moveNext()) return false;
-
-    int value = utf16CodeUnitIterator.current;
-    if (value < 0) {
-      if (replacementCodepoint != null) {
-        _current = replacementCodepoint;
-      } else {
-        throw new ArgumentError(
-            "Invalid UTF16 at ${utf16CodeUnitIterator.position}");
-      }
-    } else if (value < UNICODE_UTF16_RESERVED_LO ||
-        (value > UNICODE_UTF16_RESERVED_HI && value <= UNICODE_PLANE_ONE_MAX)) {
-      // transfer directly
-      _current = value;
-    } else if (value < UNICODE_UTF16_SURROGATE_UNIT_1_BASE &&
-        utf16CodeUnitIterator.moveNext()) {
-      // merge surrogate pair
-      int nextValue = utf16CodeUnitIterator.current;
-      if (nextValue >= UNICODE_UTF16_SURROGATE_UNIT_1_BASE &&
-          nextValue <= UNICODE_UTF16_RESERVED_HI) {
-        value = (value - UNICODE_UTF16_SURROGATE_UNIT_0_BASE) << 10;
-        value += UNICODE_UTF16_OFFSET +
-            (nextValue - UNICODE_UTF16_SURROGATE_UNIT_1_BASE);
-        _current = value;
-      } else {
-        if (nextValue >= UNICODE_UTF16_SURROGATE_UNIT_0_BASE &&
-           nextValue < UNICODE_UTF16_SURROGATE_UNIT_1_BASE) {
-          utf16CodeUnitIterator.backup();
-        }
-        if (replacementCodepoint != null) {
-          _current = replacementCodepoint;
-        } else {
-          throw new ArgumentError(
-              "Invalid UTF16 at ${utf16CodeUnitIterator.position}");
-        }
-      }
-    } else if (replacementCodepoint != null) {
-      _current = replacementCodepoint;
-    } else {
-      throw new ArgumentError(
-          "Invalid UTF16 at ${utf16CodeUnitIterator.position}");
-    }
-    return true;
-  }
-}
-
-/**
- * _ListRange in an internal type used to create a lightweight Interable on a
- * range within a source list. DO NOT MODIFY the underlying list while
- * iterating over it. The results of doing so are undefined.
- */
-// TODO(floitsch): Consider removing the extend and switch to implements since
-// that's cheaper to allocate.
-class _ListRange extends Iterable {
-  final List _source;
-  final int _offset;
-  final int _length;
-
-  _ListRange(source, [offset = 0, length]) :
-      this._source = source,
-      this._offset = offset,
-      this._length = (length == null ? source.length - offset : length) {
-    if (_offset < 0 || _offset > _source.length) {
-      throw new RangeError.value(_offset);
-    }
-    if (_length != null && (_length < 0)) {
-      throw new RangeError.value(_length);
-    }
-    if (_length + _offset > _source.length) {
-      throw new RangeError.value(_length + _offset);
-    }
-  }
-
-  _ListRangeIterator get iterator =>
-      new _ListRangeIteratorImpl(_source, _offset, _offset + _length);
-
-  int get length => _length;
-}
-
-/**
- * The _ListRangeIterator provides more capabilities than a standard iterator,
- * including the ability to get the current position, count remaining items,
- * and move forward/backward within the iterator.
- */
-abstract class _ListRangeIterator implements Iterator<int> {
-  bool moveNext();
-  int get current;
-  int get position;
-  void backup([by]);
-  int get remaining;
-  void skip([count]);
-}
-
-class _ListRangeIteratorImpl implements _ListRangeIterator {
-  final List<int> _source;
-  int _offset;
-  final int _end;
-
-  _ListRangeIteratorImpl(this._source, int offset, this._end)
-      : _offset = offset - 1;
-
-  int get current => _source[_offset];
-
-  bool moveNext() => ++_offset < _end;
-
-  int get position => _offset;
-
-  void backup([int by = 1]) {
-    _offset -= by;
-  }
-
-  int get remaining => _end - _offset - 1;
-
-  void skip([int count = 1]) {
-    _offset += count;
-  }
-}
-
diff --git a/sdk/lib/utf/utf_sources.gypi b/sdk/lib/utf/utf_sources.gypi
index b11d1f5..cb82346 100644
--- a/sdk/lib/utf/utf_sources.gypi
+++ b/sdk/lib/utf/utf_sources.gypi
@@ -7,7 +7,6 @@
   'sources': [
     'utf.dart',
     # The above file needs to be first as it lists the parts below.
-    'utf_core.dart',
     'utf_stream.dart',
     'utf8.dart',
     'utf16.dart',
diff --git a/sdk/lib/web_audio/dart2js/web_audio_dart2js.dart b/sdk/lib/web_audio/dart2js/web_audio_dart2js.dart
index 6fd8b6e..ee3553b 100644
--- a/sdk/lib/web_audio/dart2js/web_audio_dart2js.dart
+++ b/sdk/lib/web_audio/dart2js/web_audio_dart2js.dart
@@ -149,7 +149,7 @@
 
   @DomName('AudioBufferSourceNode.gain')
   @DocsEditable
-  final AudioGain gain;
+  final AudioParam gain;
 
   @DomName('AudioBufferSourceNode.loop')
   @DocsEditable
@@ -329,15 +329,6 @@
 
 
 @DocsEditable
-@DomName('AudioGain')
-class AudioGain extends AudioParam native "*AudioGain" {
-}
-// Copyright (c) 2012, 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.
-
-
-@DocsEditable
 @DomName('AudioListener')
 class AudioListener native "*AudioListener" {
 
@@ -626,7 +617,7 @@
 
   @DomName('GainNode.gain')
   @DocsEditable
-  final AudioGain gain;
+  final AudioParam gain;
 }
 // Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file
 // for details. All rights reserved. Use of this source code is governed by a
diff --git a/sdk/lib/web_audio/dartium/web_audio_dartium.dart b/sdk/lib/web_audio/dartium/web_audio_dartium.dart
index 713c60e..4b410d1 100644
--- a/sdk/lib/web_audio/dartium/web_audio_dartium.dart
+++ b/sdk/lib/web_audio/dartium/web_audio_dartium.dart
@@ -152,7 +152,7 @@
 
   @DomName('AudioBufferSourceNode.gain')
   @DocsEditable
-  AudioGain get gain native "AudioBufferSourceNode_gain_Getter";
+  AudioParam get gain native "AudioBufferSourceNode_gain_Getter";
 
   @DomName('AudioBufferSourceNode.loop')
   @DocsEditable
@@ -434,19 +434,6 @@
 
 
 @DocsEditable
-@DomName('AudioGain')
-class AudioGain extends AudioParam {
-  AudioGain.internal() : super.internal();
-
-}
-// Copyright (c) 2012, 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.
-
-// WARNING: Do not edit - generated code.
-
-
-@DocsEditable
 @DomName('AudioListener')
 class AudioListener extends NativeFieldWrapperClass1 {
   AudioListener.internal();
@@ -832,7 +819,7 @@
 
   @DomName('GainNode.gain')
   @DocsEditable
-  AudioGain get gain native "GainNode_gain_Getter";
+  AudioParam get gain native "GainNode_gain_Getter";
 
 }
 // Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file
diff --git a/tests/co19/co19-compiler.status b/tests/co19/co19-compiler.status
index b850e58..8fc530f 100644
--- a/tests/co19/co19-compiler.status
+++ b/tests/co19/co19-compiler.status
@@ -43,6 +43,8 @@
 Language/11_Expressions/32_Type_Cast_A01_t04: Fail # co19 issue 342 (class can be used anywhere, including left side of "as")
 
 
+Language/14_Types/5_Function_Types_A01_t10: Pass # co19 issue 392, issue 9058
+Language/14_Types/5_Function_Types_A02_t06: Pass # co19 issue 392, issue 9058
 Language/14_Types/5_Function_Types_A04_t01: Fail # co19 issue 345 (optional parameters list cannot by empty)
 
 Language/07_Classes/6_Constructors/1_Generative_Constructors_A04_t15: Fail # co19 issue 346 (invalid 'one ugly cascade')
diff --git a/tests/co19/co19-dart2dart.status b/tests/co19/co19-dart2dart.status
index fdd3ad2..cf39145 100644
--- a/tests/co19/co19-dart2dart.status
+++ b/tests/co19/co19-dart2dart.status
@@ -17,6 +17,8 @@
 Language/12_Statements/10_Try_A03_t02: Fail # TODO(dart2dart-team): Please triage this failure.
 Language/12_Statements/10_Try_A03_t03: Fail # TODO(dart2dart-team): Please triage this failure.
 Language/13_Libraries_and_Scripts/4_Scripts_A01_t20: Fail # TODO(dart2dart-team): Please triage this failure.
+Language/14_Types/5_Function_Types_A01_t10: Fail # co19 issue 392
+Language/14_Types/5_Function_Types_A02_t06: Fail # co19 issue 392
 Language/14_Types/5_Function_Types_A04_t01: Fail # TODO(dart2dart-team): Please triage this failure.
 Language/15_Reference/1_Lexical_Rules_A01_t09: Fail # TODO(dart2dart-team): Please triage this failure.
 Language/15_Reference/1_Lexical_Rules_A01_t11: Fail # TODO(dart2dart-team): Please triage this failure.
diff --git a/tests/co19/co19-dart2js.status b/tests/co19/co19-dart2js.status
index 5e60059..fec2e34 100644
--- a/tests/co19/co19-dart2js.status
+++ b/tests/co19/co19-dart2js.status
@@ -111,6 +111,8 @@
 Language/13_Libraries_and_Scripts/5_URIs_A01_t21: Fail # TODO(ahe): Please triage this failure.
 Language/13_Libraries_and_Scripts/5_URIs_A01_t24: Fail # TODO(ahe): Please triage this failure.
 Language/13_Libraries_and_Scripts/5_URIs_A01_t25: Fail # TODO(ahe): Please triage this failure.
+Language/14_Types/5_Function_Types_A01_t10: Pass # co19 issue 392, issue 9058
+Language/14_Types/5_Function_Types_A02_t06: Pass # co19 issue 392, issue 9058
 Language/14_Types/5_Function_Types_A04_t01: Fail # TODO(ahe): Please triage this failure.
 Language/15_Reference/1_Lexical_Rules/1_Reserved_Words_A40_t04: Fail # TODO(ahe): Please triage this failure.
 Language/15_Reference/1_Lexical_Rules_A01_t09: Fail # TODO(ahe): Please triage this failure.
@@ -711,11 +713,6 @@
 LibTest/math/atan_A01_t01: Fail, OK # co19 issue 44
 
 
-[ $compiler == dart2js && $host_checked ]
-Language/14_Types/4_Interface_Types_A11_t01: Crash # Issue 8557
-Language/14_Types/4_Interface_Types_A11_t02: Crash # Issue 8557
-
-
 #
 # The following tests are failing. Please add the error message
 # (either a compiler error or exception message). The error messages
diff --git a/tests/co19/co19-runtime.status b/tests/co19/co19-runtime.status
index 510bd96..1b41d78 100644
--- a/tests/co19/co19-runtime.status
+++ b/tests/co19/co19-runtime.status
@@ -117,6 +117,8 @@
 Language/13_Libraries_and_Scripts/5_URIs_A01_t14: Fail # Dart issue 7317
 Language/13_Libraries_and_Scripts/5_URIs_A01_t15: Fail # Dart issue 7317
 Language/13_Libraries_and_Scripts/5_URIs_A01_t21: Fail # Dart issue 6352
+Language/14_Types/5_Function_Types_A01_t10: Fail # co19 issue 392
+Language/14_Types/5_Function_Types_A02_t06: Fail # co19 issue 392
 Language/14_Types/5_Function_Types_A04_t01: Fail # Dart issue 6921
 Language/14_Types/5_Function_Types_A06_t01: Fail # Dart issue 1604
 Language/15_Reference/1_Lexical_Rules_A01_t09: Fail # Dart issue 2687
diff --git a/tests/co19/test_config.dart b/tests/co19/test_config.dart
index dc0c92f..1ea56de 100644
--- a/tests/co19/test_config.dart
+++ b/tests/co19/test_config.dart
@@ -2,10 +2,10 @@
 // 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("co19_test_config");
+library co19_test_config;
 
-#import('dart:io');
-#import('../../tools/testing/dart/test_suite.dart');
+import 'dart:io';
+import '../../tools/testing/dart/test_suite.dart';
 
 class Co19TestSuite extends StandardTestSuite {
   RegExp _testRegExp = new RegExp(r"t[0-9]{2}.dart$");
diff --git a/tests/compiler/dart2js/call_site_simple_type_inferer_test.dart b/tests/compiler/dart2js/call_site_simple_type_inferer_test.dart
index 1d1bad9..50be62e 100644
--- a/tests/compiler/dart2js/call_site_simple_type_inferer_test.dart
+++ b/tests/compiler/dart2js/call_site_simple_type_inferer_test.dart
@@ -70,7 +70,7 @@
   }
 """;
 
-const String TEST_7 = r"""
+const String TEST_7a = r"""
   class A {
     x(p) => x("x");
   }
@@ -79,12 +79,21 @@
   }
 """;
 
-const String TEST_8 = r"""
+const String TEST_7b = r"""
   class A {
-    x(p1, p2) => x(p1, "x");
+    x(p) => x("x");
   }
   main() {
-    new A().x(1, 2);
+    new A().x({});
+  }
+""";
+
+const String TEST_8 = r"""
+  class A {
+    x(p1, p2, p3) => x(p1, "x", {});
+  }
+  main() {
+    new A().x(1, 2, 3);
   }
 """;
 
@@ -222,6 +231,10 @@
   doTest(test, true, f);
 }
 
+subclassOfInterceptor(inferrer) {
+  return findTypeMask(inferrer.compiler, 'Interceptor', 'nonNullSubclass');
+}
+
 void test() {
   runTest(TEST_1, (inferrer) => [inferrer.stringType]);
   runTest(TEST_2, (inferrer) => [inferrer.intType]);
@@ -229,15 +242,19 @@
   runTest(TEST_4, (inferrer) => [inferrer.numType]);
   runTest(TEST_5, (inferrer) => [inferrer.numType]);
   runTest(TEST_6, (inferrer) => [inferrer.numType]);
-  runTest(TEST_7, (inferrer) => [inferrer.dynamicType]);
+  runTest(TEST_7a, (inferrer) => [subclassOfInterceptor(inferrer)]);
+  runTest(TEST_7b, (inferrer) => [inferrer.dynamicType]);
 
   // In the following tests, we can't infer the right types because we
   // have recursive calls with the same parameters. We should build a
   // constraint system for those, to find the types.
-  runTest(TEST_8, (inferrer) => [inferrer.dynamicType, inferrer.dynamicType]);
+  runTest(TEST_8, (inferrer) => [inferrer.dynamicType,
+                                 subclassOfInterceptor(inferrer),
+                                 inferrer.dynamicType]);
   runTest(TEST_9, (inferrer) => [inferrer.dynamicType, inferrer.dynamicType]);
   runTest(TEST_10, (inferrer) => [inferrer.dynamicType, inferrer.dynamicType]);
-  runTest(TEST_11, (inferrer) => [inferrer.dynamicType, inferrer.dynamicType]);
+  runTest(TEST_11, (inferrer) => [subclassOfInterceptor(inferrer),
+                                  subclassOfInterceptor(inferrer)]);
 
   runTest(TEST_12, (inferrer) => [inferrer.stringType, inferrer.intType]);
 
diff --git a/tests/compiler/dart2js/call_site_type_inferer_static_test.dart b/tests/compiler/dart2js/call_site_type_inferer_static_test.dart
index 4dabd93..cd049c8 100644
--- a/tests/compiler/dart2js/call_site_type_inferer_static_test.dart
+++ b/tests/compiler/dart2js/call_site_type_inferer_static_test.dart
@@ -17,7 +17,7 @@
   compiler.disableInlining = disableInlining;
   compiler.runCompiler(uri);
   var fun = findElement(compiler, functionName);
-  return check(compiler.backend, fun);
+  return check(compiler, fun);
 }
 
 // The 'f' function has an 'if' to make it non-inlinable.
@@ -74,37 +74,41 @@
 
 void doTest(String test,
             bool enableInlining,
-            List<HType> expectedTypes) {
+            List<Function> expectedTypes) {
   compileAndFind(
     test,
     'f',
     enableInlining,
-    (backend, x) {
-      HTypeList types = backend.optimisticParameterTypes(x, null);
+    (compiler, x) {
+      HTypeList types = compiler.backend.optimisticParameterTypes(x, null);
       if (expectedTypes != null) {
         Expect.isFalse(types.allUnknown);
-        Expect.listEquals(expectedTypes, types.types);
+        Expect.listEquals(expectedTypes.map((f) => f(compiler)).toList(),
+                          types.types);
       } else {
         Expect.isTrue(types.allUnknown);
       }
   });
 }
 
-void runTest(String test, [List<HType> expectedTypes]) {
+void runTest(String test, [List<Function> expectedTypes]) {
   doTest(test, false, expectedTypes);
   doTest(test, true, expectedTypes);
 }
 
 void test() {
-  runTest(TEST_ONE, [HType.STRING]);
-  runTest(TEST_TWO, [HType.INTEGER]);
-  runTest(TEST_THREE, [HType.INTEGER]);
-  runTest(TEST_FOUR, [HType.DOUBLE]);
-  runTest(TEST_FIVE, [HType.NUMBER]);
-  runTest(TEST_SIX, [HType.NUMBER]);
-  runTest(TEST_SEVEN, [HType.NON_NULL]);
-  runTest(TEST_EIGHT, [HType.INTEGER, HType.NON_NULL]);
-  runTest(TEST_NINE, [HType.NON_NULL, HType.NON_NULL]);
+  subclassOfInterceptor(compiler) =>
+      findHType(compiler, 'Interceptor', 'nonNullSubclass');
+
+  runTest(TEST_ONE, [(compiler) => HType.STRING]);
+  runTest(TEST_TWO, [(compiler) => HType.INTEGER]);
+  runTest(TEST_THREE, [(compiler) => HType.INTEGER]);
+  runTest(TEST_FOUR, [(compiler) => HType.DOUBLE]);
+  runTest(TEST_FIVE, [(compiler) => HType.NUMBER]);
+  runTest(TEST_SIX, [(compiler) => HType.NUMBER]);
+  runTest(TEST_SEVEN, [subclassOfInterceptor]);
+  runTest(TEST_EIGHT, [(compiler) => HType.INTEGER, subclassOfInterceptor]);
+  runTest(TEST_NINE, [subclassOfInterceptor, subclassOfInterceptor]);
   runTest(TEST_TEN);
 }
 
diff --git a/tests/compiler/dart2js/call_site_type_inferer_test.dart b/tests/compiler/dart2js/call_site_type_inferer_test.dart
index 2c2b529..483ff78 100644
--- a/tests/compiler/dart2js/call_site_type_inferer_test.dart
+++ b/tests/compiler/dart2js/call_site_type_inferer_test.dart
@@ -19,7 +19,7 @@
   compiler.runCompiler(uri);
   var cls = findElement(compiler, className);
   var member = cls.lookupLocalMember(buildSourceString(memberName));
-  return check(compiler.backend, member);
+  return check(compiler, member);
 }
 
 const String TEST_1 = r"""
@@ -70,7 +70,7 @@
   }
 """;
 
-const String TEST_7 = r"""
+const String TEST_7a = r"""
   class A {
     x(p) => x("x");
   }
@@ -79,12 +79,21 @@
   }
 """;
 
-const String TEST_8 = r"""
+const String TEST_7b = r"""
   class A {
-    x(p1, p2) => x(p1, "x");
+    x(p) => x("x");
   }
   main() {
-    new A().x(1, 2);
+    new A().x({});
+  }
+""";
+
+const String TEST_8 = r"""
+  class A {
+    x(p1, p2, p3) => x(p1, "x", {});
+  }
+  main() {
+    new A().x(1, 2, 3);
   }
 """;
 
@@ -202,17 +211,22 @@
 
 void doTest(String test,
             bool enableInlining,
-            List<HType> expectedTypes,
+            List expectedTypes,  // HTypes, or functions constructing HTypes.
             OptionalParameterTypes defaultTypes) {
   compileAndFind(
     test,
     'A',
     'x',
     enableInlining,
-    (backend, x) {
-      HTypeList types = backend.optimisticParameterTypes(x, defaultTypes);
+    (compiler, x) {
+      HTypeList types =
+          compiler.backend.optimisticParameterTypes(x, defaultTypes);
       if (expectedTypes != null) {
+        expectedTypes = expectedTypes
+            .map((e) => e is HType ? e : e(compiler))
+            .toList();
         Expect.isFalse(types.allUnknown);
+        Expect.equals(expectedTypes.length, types.types.length);
         Expect.listEquals(expectedTypes, types.types);
       } else {
         Expect.isTrue(types.allUnknown);
@@ -230,17 +244,21 @@
 void test() {
   OptionalParameterTypes defaultTypes;
 
+  subclassOfInterceptor(compiler) =>
+      findHType(compiler, 'Interceptor', 'nonNullSubclass');
+
   runTest(TEST_1, [HType.STRING]);
   runTest(TEST_2, [HType.INTEGER]);
   runTest(TEST_3, [HType.INTEGER]);
   runTest(TEST_4, [HType.DOUBLE]);
   runTest(TEST_5, [HType.NUMBER]);
   runTest(TEST_6, [HType.NUMBER]);
-  runTest(TEST_7, [HType.NON_NULL]);
-  runTest(TEST_8, [HType.INTEGER, HType.NON_NULL]);
+  runTest(TEST_7a, [subclassOfInterceptor]);
+  runTest(TEST_7b, [HType.NON_NULL]);
+  runTest(TEST_8, [HType.INTEGER, subclassOfInterceptor, HType.NON_NULL]);
   runTest(TEST_9, [HType.INTEGER, HType.INTEGER]);
   runTest(TEST_10, [HType.INTEGER, HType.INTEGER]);
-  runTest(TEST_11, [HType.NON_NULL, HType.NON_NULL]);
+  runTest(TEST_11, [subclassOfInterceptor, subclassOfInterceptor]);
 
   defaultTypes = new OptionalParameterTypes(1);
   defaultTypes.update(0, const SourceString("p2"), HType.INTEGER);
@@ -266,7 +284,7 @@
   defaultTypes.update(1, const SourceString("p3"), HType.STRING);
   runTest(TEST_17, [HType.INTEGER, HType.BOOLEAN, HType.DOUBLE], defaultTypes);
 
-  runTest(TEST_18, [HType.NON_NULL, HType.NON_NULL]);
+  runTest(TEST_18, [subclassOfInterceptor, subclassOfInterceptor]);
 }
 
 void main() {
diff --git a/tests/compiler/dart2js/compiler_helper.dart b/tests/compiler/dart2js/compiler_helper.dart
index d388aa9..c816160 100644
--- a/tests/compiler/dart2js/compiler_helper.dart
+++ b/tests/compiler/dart2js/compiler_helper.dart
@@ -26,6 +26,9 @@
 
 import '../../../sdk/lib/_internal/compiler/implementation/ssa/ssa.dart' as ssa;
 
+import '../../../sdk/lib/_internal/compiler/implementation/types/types.dart'
+       as types;
+
 import '../../../sdk/lib/_internal/compiler/implementation/util/util.dart';
 export '../../../sdk/lib/_internal/compiler/implementation/util/util.dart';
 
@@ -123,6 +126,33 @@
   return element;
 }
 
+types.TypeMask findTypeMask(compiler, String name,
+                            [String how = 'nonNullExact']) {
+  var sourceName = buildSourceString(name);
+  var element = compiler.mainApp.find(sourceName);
+  if (element == null) {
+    element = compiler.interceptorsLibrary.find(sourceName);
+  }
+  if (element == null) {
+    element = compiler.coreLibrary.find(sourceName);
+  }
+  Expect.isNotNull(element, 'Could not locate $name');
+  var dartType = element.computeType(compiler);
+  switch (how) {
+    case 'exact': return new types.TypeMask.exact(dartType);
+    case 'nonNullExact': return new types.TypeMask.nonNullExact(dartType);
+    case 'subclass': return new types.TypeMask.subclass(dartType);
+    case 'nonNullSubclass': return new types.TypeMask.nonNullSubclass(dartType);
+    case 'subtype': return new types.TypeMask.subtype(dartType);
+    case 'nonNullSubtype': return new types.TypeMask.nonNullSubtype(dartType);
+  }
+  Expect.fail('Unknown HType constructor $how');
+}
+
+ssa.HType findHType(compiler, String name, [String how = 'nonNullExact']) {
+  return new ssa.HType.fromMask(findTypeMask(compiler, name, how), compiler);
+}
+
 String anyIdentifier = "[a-zA-Z][a-zA-Z0-9]*";
 
 String getIntTypeCheck(String variable) {
diff --git a/tests/compiler/dart2js/constant_namer_test.dart b/tests/compiler/dart2js/constant_namer_test.dart
new file mode 100644
index 0000000..0816c8b
--- /dev/null
+++ b/tests/compiler/dart2js/constant_namer_test.dart
@@ -0,0 +1,35 @@
+// Copyright (c) 2013, 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 'compiler_helper.dart';
+
+const String TEST_ONE = r"""
+  class Token {
+    final name;
+    final value;
+    const Token(this.name, [this.value]);
+    use() { print(this); }
+  }
+  test() {
+    const [12,53].use();
+    const Token('start').use();
+    const Token('end').use();
+    const Token('yes', 12).use();
+    const Token(true, false).use();
+  }
+""";
+
+main() {
+  check(generated, text) {
+    Expect.isTrue(generated.contains(text), text);
+  }
+
+  var generated = compile(TEST_ONE, entry: 'test');
+
+  check(generated, '.List_12_53.');
+  check(generated, '.Token_start_null.');
+  check(generated, '.Token_end_null.');
+  check(generated, '.Token_yes_12.');
+  check(generated, '.Token_true_false.');
+}
diff --git a/tests/compiler/dart2js/deferred_load_graph_segmentation_test.dart b/tests/compiler/dart2js/deferred_load_graph_segmentation_test.dart
index b5dc726..61a1e65 100644
--- a/tests/compiler/dart2js/deferred_load_graph_segmentation_test.dart
+++ b/tests/compiler/dart2js/deferred_load_graph_segmentation_test.dart
@@ -17,7 +17,7 @@
        as dart2js;
 
 import '../../../sdk/lib/_internal/compiler/implementation/filenames.dart'
-       show getCurrentDirectory;
+       show getCurrentDirectory, nativeToUriPath;
 
 import '../../../sdk/lib/_internal/compiler/implementation/source_file.dart'
        show SourceFile;
@@ -42,7 +42,7 @@
 
 void main() {
   Uri cwd = getCurrentDirectory();
-  Uri script = cwd.resolve(new Options().script);
+  Uri script = cwd.resolve(nativeToUriPath(new Options().script));
   Uri libraryRoot = script.resolve('../../../sdk/');
   Uri packageRoot = script.resolve('./packages/');
 
diff --git a/tests/compiler/dart2js/field_type_inferer_test.dart b/tests/compiler/dart2js/field_type_inferer_test.dart
index d791841..ee5cb28 100644
--- a/tests/compiler/dart2js/field_type_inferer_test.dart
+++ b/tests/compiler/dart2js/field_type_inferer_test.dart
@@ -335,8 +335,8 @@
   }
 """;
 
-void doTest(String test, bool disableInlining, Map<String, HType> fields) {
-  fields.forEach((String name, HType type) {
+void doTest(String test, bool disableInlining, Map<String, dynamic> fields) {
+  fields.forEach((String name, type) {
     compileAndFind(
       test,
       'A',
@@ -344,6 +344,7 @@
       disableInlining,
       (backend, field) {
         HType inferredType = backend.optimisticFieldType(field);
+        if (type is Function) type = type(backend.compiler);
         Expect.equals(type, inferredType);
     });
   });
@@ -355,10 +356,13 @@
 }
 
 void test() {
+  HType interceptorType(compiler) =>
+      findHType(compiler, 'Interceptor', 'nonNullSubclass');
+
   runTest(TEST_1, {'f': HType.NULL});
   runTest(TEST_2, {'f1': HType.NULL, 'f2': HType.INTEGER});
   runTest(TEST_3, {'f1': HType.INTEGER, 'f2': HType.INTEGER_OR_NULL});
-  runTest(TEST_4, {'f1': HType.NON_NULL, 'f2': HType.STRING_OR_NULL});
+  runTest(TEST_4, {'f1': interceptorType, 'f2': HType.STRING_OR_NULL});
   runTest(TEST_5, {'f1': HType.STRING, 'f2': HType.STRING});
   runTest(TEST_6, {'f1': HType.STRING, 'f2': HType.EXTENDABLE_ARRAY});
   runTest(TEST_7, {'f1': HType.INDEXABLE_PRIMITIVE,
diff --git a/tests/compiler/dart2js/field_type_simple_inferer_test.dart b/tests/compiler/dart2js/field_type_simple_inferer_test.dart
index 03e83cb..47dc130 100644
--- a/tests/compiler/dart2js/field_type_simple_inferer_test.dart
+++ b/tests/compiler/dart2js/field_type_simple_inferer_test.dart
@@ -437,7 +437,7 @@
       (inferrer, field) {
         TypeMask type = f(inferrer);
         TypeMask inferredType = inferrer.typeOf[field];
-        Expect.equals(type, inferredType);
+        Expect.equals(type, inferredType, name);
     });
   });
 }
@@ -448,31 +448,36 @@
 }
 
 void test() {
+  subclassOfInterceptor(inferrer) =>
+      findTypeMask(inferrer.compiler, 'Interceptor', 'nonNullSubclass');
+  dynamicType(inferrer) => inferrer.dynamicType;
+
   runTest(TEST_1, {'f': (inferrer) => inferrer.nullType});
   runTest(TEST_2, {'f1': (inferrer) => inferrer.nullType,
                    'f2': (inferrer) => inferrer.intType});
   runTest(TEST_3, {'f1': (inferrer) => inferrer.intType,
                    'f2': (inferrer) => inferrer.intType.nullable()});
-  runTest(TEST_4, {'f1': (inferrer) => inferrer.dynamicType,
+  runTest(TEST_4, {'f1': subclassOfInterceptor,
                    'f2': (inferrer) => inferrer.stringType.nullable()});
 
   // TODO(ngeoffray): We should try to infer that the initialization
   // code at the declaration site of the fields does not matter.
-  runTest(TEST_5, {'f1': (inferrer) => inferrer.dynamicType,
-                   'f2': (inferrer) => inferrer.dynamicType});
-  runTest(TEST_6, {'f1': (inferrer) => inferrer.dynamicType,
-                   'f2': (inferrer) => inferrer.dynamicType});
-  runTest(TEST_7, {'f1': (inferrer) => inferrer.dynamicType,
-                   'f2': (inferrer) => inferrer.dynamicType});
+  runTest(TEST_5, {'f1': subclassOfInterceptor,
+                   'f2': subclassOfInterceptor});
+  // TODO(9415). These tests seem flaky.
+  //runTest(TEST_6, {'f1': subclassOfInterceptor,
+  //                 'f2': subclassOfInterceptor});
+  //runTest(TEST_7, {'f1': subclassOfInterceptor,
+  //                 'f2': subclassOfInterceptor});
 
   runTest(TEST_8, {'f': (inferrer) => inferrer.stringType.nullable()});
   runTest(TEST_9, {'f': (inferrer) => inferrer.stringType.nullable()});
-  runTest(TEST_10, {'f': (inferrer) => inferrer.dynamicType});
+  runTest(TEST_10, {'f': subclassOfInterceptor});
   runTest(TEST_11, {'fs': (inferrer) => inferrer.intType});
 
   // TODO(ngeoffray): We should try to infer that the initialization
   // code at the declaration site of the fields does not matter.
-  runTest(TEST_12, {'fs': (inferrer) => inferrer.dynamicType});
+  runTest(TEST_12, {'fs': subclassOfInterceptor});
 
   runTest(TEST_13, {'fs': (inferrer) => inferrer.intType});
   runTest(TEST_14, {'f': (inferrer) => inferrer.intType});
@@ -481,7 +486,7 @@
                                 inferrer.compiler.backend.jsIndexableClass;
                             return new TypeMask.nonNullSubtype(cls.rawType);
                          }});
-  runTest(TEST_16, {'f': (inferrer) => inferrer.dynamicType});
+  runTest(TEST_16, {'f': subclassOfInterceptor});
   runTest(TEST_17, {'f': (inferrer) => inferrer.intType.nullable()});
   runTest(TEST_18, {'f1': (inferrer) => inferrer.intType,
                     'f2': (inferrer) => inferrer.stringType,
diff --git a/tests/compiler/dart2js/interpolation_folding_test.dart b/tests/compiler/dart2js/interpolation_folding_test.dart
new file mode 100644
index 0000000..3734fd9
--- /dev/null
+++ b/tests/compiler/dart2js/interpolation_folding_test.dart
@@ -0,0 +1,57 @@
+// Copyright (c) 2013, 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 'compiler_helper.dart';
+
+// Tests for
+const String TEST_1 = r"""
+  foo() {
+    int a = 120;
+    String b = 'hello';
+    return 'u${a}v${b}w';
+  }
+""";
+
+const String TEST_2 = r"""
+  foo(a, b) {
+    return 'aaaaa${a}xxxxx'
+           "yyyyy${b}zzzzz";
+  }
+""";
+
+const String TEST_3 = r"""
+  foo(a) {
+    var b = '$a#';
+    return '${b}x${b}';
+  }
+""";
+
+const String TEST_4 = r"""
+  foo(a) {
+    var b = [];
+    if (a) b.add(123);
+    return '${b.length}';
+  }
+""";
+
+main() {
+  void check(String test, String contained) {
+    var generated = compile(test, entry: 'foo');
+    Expect.isTrue(generated.contains(contained), contained);
+  }
+
+  // Full substitution.
+  check(TEST_1, r'"u120vhellow"');
+
+  // Adjacent string fragments get merged.
+  check(TEST_2, r'"xxxxxyyyyy"');
+
+  // 1. No merging of fragments that are multi-use.  Prevents exponential code
+  //    and keeps author's manual CSE.
+  // 2. Know string values require no stringification.
+  check(TEST_3, r'return b + "x" + b');
+
+  // Known int value can be formatted directly.
+  check(TEST_4, r'return "" + b.length');
+}
diff --git a/tests/compiler/dart2js/mock_compiler.dart b/tests/compiler/dart2js/mock_compiler.dart
index 6e52aae..adbdc76 100644
--- a/tests/compiler/dart2js/mock_compiler.dart
+++ b/tests/compiler/dart2js/mock_compiler.dart
@@ -70,8 +70,12 @@
      var arg7, var arg8, var arg9, var arg10, var arg11]) {}''';
 
 const String DEFAULT_INTERCEPTORSLIB = r'''
+  class Interceptor {
+    toString() {}
+    bool operator==(other) => identical(this, other);
+  }
   class JSIndexable {}
-  class JSArray implements List, JSIndexable {
+  class JSArray extends Interceptor implements List, JSIndexable {
     var length;
     operator[](index) {}
     operator[]=(index, value) {}
@@ -80,12 +84,12 @@
   class JSMutableArray extends JSArray {}
   class JSFixedArray extends JSMutableArray {}
   class JSExtendableArray extends JSMutableArray {}
-  class JSString implements String, JSIndexable {
+  class JSString extends Interceptor implements String, JSIndexable {
     var length;
     operator[](index) {}
     toString() {}
   }
-  class JSNumber implements num {
+  class JSNumber extends Interceptor implements num {
     // All these methods return a number to please type inferencing.
     operator-() => (this is JSInt) ? 42 : 42.0;
     operator +(other) => (this is JSInt) ? 42 : 42.0;
@@ -110,11 +114,12 @@
   }
   class JSDouble extends JSNumber implements double {
   }
-  class JSNull {
+  class JSNull extends Interceptor {
+    bool operator==(other) => identical(null, other);
   }
-  class JSBool implements bool {
+  class JSBool extends Interceptor implements bool {
   }
-  class JSFunction implements Function {
+  class JSFunction extends Interceptor implements Function {
   }
   class ObjectInterceptor {
   }
diff --git a/tests/compiler/dart2js/return_type_inferer_test.dart b/tests/compiler/dart2js/return_type_inferer_test.dart
index 6878a80..ae7ce7e 100644
--- a/tests/compiler/dart2js/return_type_inferer_test.dart
+++ b/tests/compiler/dart2js/return_type_inferer_test.dart
@@ -63,7 +63,7 @@
   main() { f(1); g(f); }
 """;
 
-void runTest(String test, [HType expectedType = HType.UNKNOWN]) {
+void runTest(String test, Function findExpectedType) {
   compileAndCheck(
     test,
     'f',
@@ -71,21 +71,24 @@
       var backend = compiler.backend;
       HType type =
           backend.optimisticReturnTypesWithRecompilationOnTypeChange(null, x);
-      Expect.equals(expectedType, type);
+      Expect.equals(findExpectedType(compiler), type);
   });
 }
 
 void test() {
-  runTest(TEST_ONE, HType.STRING);
-  runTest(TEST_TWO, HType.INTEGER);
-  runTest(TEST_THREE, HType.INTEGER);
-  runTest(TEST_FOUR, HType.DOUBLE);
-  runTest(TEST_FIVE, HType.NUMBER);
-  runTest(TEST_SIX, HType.NUMBER);
-  runTest(TEST_SEVEN, HType.NON_NULL);
-  runTest(TEST_EIGHT, HType.INTEGER);
-  runTest(TEST_NINE, HType.NON_NULL);
-  runTest(TEST_TEN);
+  subclassOfInterceptor(compiler) =>
+      findHType(compiler, 'Interceptor', 'nonNullSubclass');
+
+  runTest(TEST_ONE, (compiler) => HType.STRING);
+  runTest(TEST_TWO, (compiler) => HType.INTEGER);
+  runTest(TEST_THREE, (compiler) => HType.INTEGER);
+  runTest(TEST_FOUR, (compiler) => HType.DOUBLE);
+  runTest(TEST_FIVE, (compiler) => HType.NUMBER);
+  runTest(TEST_SIX, (compiler) => HType.NUMBER);
+  runTest(TEST_SEVEN, subclassOfInterceptor);
+  runTest(TEST_EIGHT, (compiler) => HType.INTEGER);
+  runTest(TEST_NINE, subclassOfInterceptor);
+  runTest(TEST_TEN, (compiler) => HType.UNKNOWN);
 }
 
 void main() {
diff --git a/tests/compiler/dart2js/simple_inferrer_and_or_test.dart b/tests/compiler/dart2js/simple_inferrer_and_or_test.dart
index c98657f..8b34146 100644
--- a/tests/compiler/dart2js/simple_inferrer_and_or_test.dart
+++ b/tests/compiler/dart2js/simple_inferrer_and_or_test.dart
@@ -5,6 +5,7 @@
 import 'compiler_helper.dart';
 
 const String TEST = """
+class X {}
 returnDyn1() {
   var a;
   ((a = 52) == true) || ((a = 'foo') == true);
@@ -23,10 +24,31 @@
   return a;
 }
 
+returnDyn4() {
+  var a;
+  ((a = 52) == true) || ((a = new X()) == true);
+  return a;
+}
+
+returnDyn5() {
+  var a;
+  ((a = 52) == true) && ((a = new X()) == true);
+  return a;
+}
+
+returnDyn6() {
+  var a;
+  a = a == 54 ? 'foo' : new X();
+  return a;
+}
+
 main() {
   returnDyn1();
   returnDyn2();
   returnDyn3();
+  returnDyn4();
+  returnDyn5();
+  returnDyn6();
 }
 """;
 
@@ -42,7 +64,13 @@
     Expect.equals(type, typesInferrer.returnTypeOf[element]);
   }
 
-  checkReturn('returnDyn1', typesInferrer.dynamicType);
-  checkReturn('returnDyn2', typesInferrer.dynamicType);
-  checkReturn('returnDyn3', typesInferrer.dynamicType);
+  var subclassOfInterceptor =
+      findTypeMask(compiler, 'Interceptor', 'nonNullSubclass');
+
+  checkReturn('returnDyn1', subclassOfInterceptor);
+  checkReturn('returnDyn2', subclassOfInterceptor);
+  checkReturn('returnDyn3', subclassOfInterceptor);
+  checkReturn('returnDyn4', typesInferrer.dynamicType);
+  checkReturn('returnDyn5', typesInferrer.dynamicType);
+  checkReturn('returnDyn6', typesInferrer.dynamicType);
 }
diff --git a/tests/compiler/dart2js/simple_inferrer_final_field3_test.dart b/tests/compiler/dart2js/simple_inferrer_final_field3_test.dart
index 653f543..de30794 100644
--- a/tests/compiler/dart2js/simple_inferrer_final_field3_test.dart
+++ b/tests/compiler/dart2js/simple_inferrer_final_field3_test.dart
@@ -33,5 +33,6 @@
     Expect.equals(type, typesInferrer.typeOf[element]);
   }
 
-  checkFieldTypeInClass('A', 'dynamicField', typesInferrer.dynamicType);
+  checkFieldTypeInClass('A', 'dynamicField',
+      findTypeMask(compiler, 'Interceptor', 'nonNullSubclass'));
 }
diff --git a/tests/compiler/dart2js/simple_inferrer_final_field_test.dart b/tests/compiler/dart2js/simple_inferrer_final_field_test.dart
index 6da3bd1..b525e3f 100644
--- a/tests/compiler/dart2js/simple_inferrer_final_field_test.dart
+++ b/tests/compiler/dart2js/simple_inferrer_final_field_test.dart
@@ -9,10 +9,11 @@
 
 class A {
   final intField;
-  final giveUpField;
+  final giveUpField1;
+  final giveUpField2;
   final fieldParameter;
-  A() : intField = 42, giveUpField = 'foo';
-  A.bar() : intField = 54, giveUpField = 42;
+  A() : intField = 42, giveUpField1 = 'foo', giveUpField2 = 'foo';
+  A.bar() : intField = 54, giveUpField1 = 42, giveUpField2 = new A();
   A.foo(this.fieldParameter);
 }
 
@@ -36,6 +37,8 @@
   }
 
   checkFieldTypeInClass('A', 'intField', typesInferrer.intType);
-  checkFieldTypeInClass('A', 'giveUpField', typesInferrer.dynamicType);
+  checkFieldTypeInClass('A', 'giveUpField1',
+      findTypeMask(compiler, 'Interceptor', 'nonNullSubclass'));
+  checkFieldTypeInClass('A', 'giveUpField2', typesInferrer.dynamicType);
   checkFieldTypeInClass('A', 'fieldParameter', typesInferrer.intType);
 }
diff --git a/tests/compiler/dart2js/simple_inferrer_postfix_prefix_test.dart b/tests/compiler/dart2js/simple_inferrer_postfix_prefix_test.dart
index 144b2d0..6e029f6 100644
--- a/tests/compiler/dart2js/simple_inferrer_postfix_prefix_test.dart
+++ b/tests/compiler/dart2js/simple_inferrer_postfix_prefix_test.dart
@@ -71,14 +71,17 @@
     Expect.equals(type, typesInferrer.returnTypeOf[element]);
   }
 
+  var subclassOfInterceptor =
+      findTypeMask(compiler, 'Interceptor', 'nonNullSubclass');
+
   checkReturnInClass('A', 'returnNum1', typesInferrer.numType);
   checkReturnInClass('A', 'returnNum2', typesInferrer.numType);
   checkReturnInClass('A', 'returnNum3', typesInferrer.numType);
   checkReturnInClass('A', 'returnNum4', typesInferrer.numType);
   checkReturnInClass('A', 'returnNum5', typesInferrer.numType);
   checkReturnInClass('A', 'returnNum6', typesInferrer.numType);
-  checkReturnInClass('A', 'returnDynamic1', typesInferrer.dynamicType);
-  checkReturnInClass('A', 'returnDynamic2', typesInferrer.dynamicType);
+  checkReturnInClass('A', 'returnDynamic1', subclassOfInterceptor);
+  checkReturnInClass('A', 'returnDynamic2', subclassOfInterceptor);
   checkReturnInClass('A', 'returnDynamic3', typesInferrer.dynamicType);
 
   checkReturnInClass('B', 'returnString1', typesInferrer.stringType);
diff --git a/tests/compiler/dart2js/simple_inferrer_test.dart b/tests/compiler/dart2js/simple_inferrer_test.dart
index ba3721c..3e1e86f 100644
--- a/tests/compiler/dart2js/simple_inferrer_test.dart
+++ b/tests/compiler/dart2js/simple_inferrer_test.dart
@@ -136,14 +136,17 @@
 
   checkReturn(String name, type) {
     var element = findElement(compiler, name);
-    Expect.equals(type, typesInferrer.returnTypeOf[element]);
+    Expect.equals(type, typesInferrer.returnTypeOf[element], name);
   }
+  var interceptorType =
+      findTypeMask(compiler, 'Interceptor', 'nonNullSubclass');
+
   checkReturn('returnNum1', typesInferrer.numType);
   checkReturn('returnNum2', typesInferrer.numType);
   checkReturn('returnInt1', typesInferrer.intType);
   checkReturn('returnInt2', typesInferrer.intType);
   checkReturn('returnDouble', typesInferrer.doubleType);
-  checkReturn('returnGiveUp', typesInferrer.dynamicType);
+  checkReturn('returnGiveUp', interceptorType);
   checkReturn('returnNum3', typesInferrer.numType);
   checkReturn('returnNum4', typesInferrer.numType);
   checkReturn('returnIntOrNull', typesInferrer.intType.nullable());
@@ -163,7 +166,7 @@
   checkReturnInClass('A', 'returnNum4', typesInferrer.numType);
   checkReturnInClass('A', 'returnNum5', typesInferrer.numType);
   checkReturnInClass('A', 'returnNum6', typesInferrer.numType);
-  checkReturnInClass('A', '==', typesInferrer.dynamicType);
+  checkReturnInClass('A', '==', interceptorType);
 
   checkReturnInClass('B', 'returnNum1', typesInferrer.numType);
   checkReturnInClass('B', 'returnNum2', typesInferrer.numType);
diff --git a/tests/compiler/dart2js/simple_inferrer_try_catch_test.dart b/tests/compiler/dart2js/simple_inferrer_try_catch_test.dart
index be8f90e..3370dbe 100644
--- a/tests/compiler/dart2js/simple_inferrer_try_catch_test.dart
+++ b/tests/compiler/dart2js/simple_inferrer_try_catch_test.dart
@@ -171,10 +171,13 @@
   checkReturn('returnInt6',
       new TypeMask.nonNullSubtype(compiler.intClass.rawType));
 
-  checkReturn('returnDyn1', typesInferrer.dynamicType);
-  checkReturn('returnDyn2', typesInferrer.dynamicType);
-  checkReturn('returnDyn3', typesInferrer.dynamicType);
-  checkReturn('returnDyn4', typesInferrer.dynamicType);
-  checkReturn('returnDyn5', typesInferrer.dynamicType);
+  var subclassOfInterceptor =
+      findTypeMask(compiler, 'Interceptor', 'nonNullSubclass');
+
+  checkReturn('returnDyn1', subclassOfInterceptor);
+  checkReturn('returnDyn2', subclassOfInterceptor);
+  checkReturn('returnDyn3', subclassOfInterceptor);
+  checkReturn('returnDyn4', subclassOfInterceptor);
+  checkReturn('returnDyn5', subclassOfInterceptor);
   checkReturn('returnDyn6', typesInferrer.dynamicType);
 }
diff --git a/tests/compiler/dart2js/type_combination_test.dart b/tests/compiler/dart2js/type_combination_test.dart
index f978334..246a7fa 100644
--- a/tests/compiler/dart2js/type_combination_test.dart
+++ b/tests/compiler/dart2js/type_combination_test.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 "mock_compiler.dart";
+import "compiler_helper.dart";
 import "parser_helper.dart";
 import "../../../sdk/lib/_internal/compiler/implementation/ssa/ssa.dart";
 import "../../../sdk/lib/_internal/compiler/implementation/types/types.dart";
@@ -32,2003 +32,635 @@
 HType nonPrimitive2;
 HType potentialArray;
 HType potentialString;
+HType jsInterceptor;
 
 HType jsArrayOrNull;
 HType jsMutableArrayOrNull;
 HType jsFixedArrayOrNull;
 HType jsExtendableArrayOrNull;
 HType jsIndexableOrNull;
+HType jsInterceptorOrNull;
+
+
+class Pair {
+  final first;
+  final second;
+  Pair(this.first, this.second);
+  int get hashCode => first.hashCode * 47 + second.hashCode;
+  bool operator==(Pair other) =>
+      identical(first, other.first) && identical(second, other.second);
+}
+
+class RuleSet {
+  final name;
+  final operate;
+  final Set typesSeen = new Set();
+  final Set pairsSeen = new Set();
+
+  RuleSet(this.name, this.operate);
+
+  void rule(type1, type2, result) {
+    typesSeen..add(type1)..add(type2);
+    var pair1 = new Pair(type1, type2);
+    var pair2 = new Pair(type2, type1);
+    if (pairsSeen.contains(pair1)) {
+      Expect.isFalse(true, 'Redundant rule ($type1, $type2, ...)');
+    }
+    pairsSeen..add(pair1)..add(pair2);
+
+    var r1 = operate(type1, type2);
+    var r2 = operate(type2, type1);
+    Expect.equals(result, r1);
+    Expect.equals(r1, r2, 'symmetry violation');
+  }
+
+  void check(type1, type2, predicate) {
+    typesSeen..add(type1)..add(type2);
+    var pair = new Pair(type1, type2);
+    pairsSeen..add(pair);
+    var result = operate(type1, type2);
+    Expect.isTrue(predicate(result));
+  }
+
+  void validateCoverage() {
+    for (var type1 in typesSeen) {
+      for (var type2 in typesSeen) {
+        var pair = new Pair(type1, type2);
+        if (!pairsSeen.contains(pair)) {
+          Expect.isTrue(false, 'Missing rule: $name($type1, $type2)');
+        }
+      }
+    }
+  }
+}
 
 void testUnion(MockCompiler compiler) {
-  Expect.equals(CONFLICTING,
-                CONFLICTING.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                CONFLICTING.union(UNKNOWN, compiler));
-  Expect.equals(BOOLEAN,
-                CONFLICTING.union(BOOLEAN, compiler));
-  Expect.equals(NUMBER,
-                CONFLICTING.union(NUMBER, compiler));
-  Expect.equals(INTEGER,
-                CONFLICTING.union(INTEGER, compiler));
-  Expect.equals(DOUBLE,
-                CONFLICTING.union(DOUBLE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                CONFLICTING.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(STRING,
-                CONFLICTING.union(STRING, compiler));
-  Expect.equals(READABLE_ARRAY,
-                CONFLICTING.union(READABLE_ARRAY, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                CONFLICTING.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                CONFLICTING.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(nonPrimitive1,
-                CONFLICTING.union(nonPrimitive1, compiler));
-  Expect.equals(nonPrimitive2,
-                CONFLICTING.union(nonPrimitive2, compiler));
-  Expect.equals(potentialArray,
-                CONFLICTING.union(potentialArray, compiler));
-  Expect.equals(potentialString,
-                CONFLICTING.union(potentialString, compiler));
-  Expect.equals(BOOLEAN_OR_NULL,
-                CONFLICTING.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                CONFLICTING.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                CONFLICTING.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                CONFLICTING.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(STRING_OR_NULL,
-                CONFLICTING.union(STRING_OR_NULL, compiler));
-  Expect.equals(NULL,
-                CONFLICTING.union(NULL, compiler));
-  Expect.equals(FIXED_ARRAY,
-                CONFLICTING.union(FIXED_ARRAY, compiler));
+  RuleSet ruleSet = new RuleSet('union', (t1, t2) => t1.union(t2, compiler));
+  rule(type1, type2, result) => ruleSet.rule(type1, type2, result);
+  check(type1, type2, predicate) => ruleSet.check(type1, type2, predicate);
 
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(UNKNOWN, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(BOOLEAN, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(NUMBER, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(INTEGER, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(DOUBLE, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(STRING, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(READABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(nonPrimitive1, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(STRING_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(NULL, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.union(FIXED_ARRAY, compiler));
+  rule(CONFLICTING, CONFLICTING, CONFLICTING);
+  rule(CONFLICTING, UNKNOWN, UNKNOWN);
+  rule(CONFLICTING, BOOLEAN, BOOLEAN);
+  rule(CONFLICTING, NUMBER, NUMBER);
+  rule(CONFLICTING, INTEGER, INTEGER);
+  rule(CONFLICTING, DOUBLE, DOUBLE);
+  rule(CONFLICTING, INDEXABLE_PRIMITIVE, INDEXABLE_PRIMITIVE);
+  rule(CONFLICTING, STRING, STRING);
+  rule(CONFLICTING, READABLE_ARRAY, READABLE_ARRAY);
+  rule(CONFLICTING, MUTABLE_ARRAY, MUTABLE_ARRAY);
+  rule(CONFLICTING, EXTENDABLE_ARRAY, EXTENDABLE_ARRAY);
+  rule(CONFLICTING, nonPrimitive1, nonPrimitive1);
+  rule(CONFLICTING, nonPrimitive2, nonPrimitive2);
+  rule(CONFLICTING, potentialArray, potentialArray);
+  rule(CONFLICTING, potentialString, potentialString);
+  rule(CONFLICTING, BOOLEAN_OR_NULL, BOOLEAN_OR_NULL);
+  rule(CONFLICTING, NUMBER_OR_NULL, NUMBER_OR_NULL);
+  rule(CONFLICTING, INTEGER_OR_NULL, INTEGER_OR_NULL);
+  rule(CONFLICTING, DOUBLE_OR_NULL, DOUBLE_OR_NULL);
+  rule(CONFLICTING, STRING_OR_NULL, STRING_OR_NULL);
+  rule(CONFLICTING, NULL, NULL);
+  rule(CONFLICTING, FIXED_ARRAY, FIXED_ARRAY);
 
-  Expect.equals(BOOLEAN,
-                BOOLEAN.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN.union(UNKNOWN, compiler));
-  Expect.equals(BOOLEAN,
-                BOOLEAN.union(BOOLEAN, compiler));
-  Expect.equals(NON_NULL,
-                BOOLEAN.union(NUMBER, compiler));
-  Expect.equals(NON_NULL,
-                BOOLEAN.union(INTEGER, compiler));
-  Expect.equals(NON_NULL,
-                BOOLEAN.union(DOUBLE, compiler));
-  Expect.equals(NON_NULL,
-                BOOLEAN.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(NON_NULL,
-                BOOLEAN.union(STRING, compiler));
-  Expect.equals(NON_NULL,
-                BOOLEAN.union(READABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                BOOLEAN.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                BOOLEAN.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                BOOLEAN.union(nonPrimitive1, compiler));
-  Expect.equals(NON_NULL,
-                BOOLEAN.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN.union(potentialString, compiler));
-  Expect.equals(BOOLEAN_OR_NULL,
-                BOOLEAN.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN.union(STRING_OR_NULL, compiler));
-  Expect.equals(BOOLEAN_OR_NULL,
-                BOOLEAN.union(NULL, compiler));
-  Expect.equals(NON_NULL,
-                BOOLEAN.union(FIXED_ARRAY, compiler));
+  rule(UNKNOWN, UNKNOWN, UNKNOWN);
+  rule(UNKNOWN, BOOLEAN, UNKNOWN);
+  rule(UNKNOWN, NUMBER, UNKNOWN);
+  rule(UNKNOWN, INTEGER, UNKNOWN);
+  rule(UNKNOWN, DOUBLE, UNKNOWN);
+  rule(UNKNOWN, INDEXABLE_PRIMITIVE, UNKNOWN);
+  rule(UNKNOWN, STRING, UNKNOWN);
+  rule(UNKNOWN, READABLE_ARRAY, UNKNOWN);
+  rule(UNKNOWN, MUTABLE_ARRAY, UNKNOWN);
+  rule(UNKNOWN, EXTENDABLE_ARRAY, UNKNOWN);
+  rule(UNKNOWN, nonPrimitive1, UNKNOWN);
+  rule(UNKNOWN, nonPrimitive2, UNKNOWN);
+  rule(UNKNOWN, potentialArray, UNKNOWN);
+  rule(UNKNOWN, potentialString, UNKNOWN);
+  rule(UNKNOWN, BOOLEAN_OR_NULL, UNKNOWN);
+  rule(UNKNOWN, NUMBER_OR_NULL, UNKNOWN);
+  rule(UNKNOWN, INTEGER_OR_NULL, UNKNOWN);
+  rule(UNKNOWN, DOUBLE_OR_NULL, UNKNOWN);
+  rule(UNKNOWN, STRING_OR_NULL, UNKNOWN);
+  rule(UNKNOWN, NULL, UNKNOWN);
+  rule(UNKNOWN, FIXED_ARRAY, UNKNOWN);
 
-  Expect.equals(NUMBER,
-                NUMBER.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER.union(UNKNOWN, compiler));
-  Expect.equals(NON_NULL,
-                NUMBER.union(BOOLEAN, compiler));
-  Expect.equals(NUMBER,
-                NUMBER.union(NUMBER, compiler));
-  Expect.equals(NUMBER,
-                NUMBER.union(INTEGER, compiler));
-  Expect.equals(NUMBER,
-                NUMBER.union(DOUBLE, compiler));
-  Expect.equals(NON_NULL,
-                NUMBER.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(NON_NULL,
-                NUMBER.union(STRING, compiler));
-  Expect.equals(NON_NULL,
-                NUMBER.union(READABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                NUMBER.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                NUMBER.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                NUMBER.union(nonPrimitive1, compiler));
-  Expect.equals(NON_NULL,
-                NUMBER.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER.union(STRING_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER.union(NULL, compiler));
-  Expect.equals(NON_NULL,
-                NUMBER.union(FIXED_ARRAY, compiler));
+  rule(BOOLEAN, BOOLEAN, BOOLEAN);
+  rule(BOOLEAN, NUMBER, jsInterceptor);
+  rule(BOOLEAN, INTEGER, jsInterceptor);
+  rule(BOOLEAN, DOUBLE, jsInterceptor);
+  rule(BOOLEAN, INDEXABLE_PRIMITIVE, NON_NULL);
+  rule(BOOLEAN, STRING, jsInterceptor);
+  rule(BOOLEAN, READABLE_ARRAY, jsInterceptor);
+  rule(BOOLEAN, MUTABLE_ARRAY, jsInterceptor);
+  rule(BOOLEAN, EXTENDABLE_ARRAY, jsInterceptor);
+  rule(BOOLEAN, nonPrimitive1, NON_NULL);
+  rule(BOOLEAN, nonPrimitive2, NON_NULL);
+  rule(BOOLEAN, potentialArray, UNKNOWN);
+  rule(BOOLEAN, potentialString, UNKNOWN);
+  rule(BOOLEAN, BOOLEAN_OR_NULL, BOOLEAN_OR_NULL);
+  rule(BOOLEAN, NUMBER_OR_NULL, jsInterceptorOrNull);
+  rule(BOOLEAN, INTEGER_OR_NULL, jsInterceptorOrNull);
+  rule(BOOLEAN, DOUBLE_OR_NULL, jsInterceptorOrNull);
+  rule(BOOLEAN, STRING_OR_NULL, jsInterceptorOrNull);
+  rule(BOOLEAN, NULL, BOOLEAN_OR_NULL);
+  rule(BOOLEAN, FIXED_ARRAY, jsInterceptor);
 
-  Expect.equals(INTEGER,
-                INTEGER.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER.union(UNKNOWN, compiler));
-  Expect.equals(NON_NULL,
-                INTEGER.union(BOOLEAN, compiler));
-  Expect.equals(NUMBER,
-                INTEGER.union(NUMBER, compiler));
-  Expect.equals(INTEGER,
-                INTEGER.union(INTEGER, compiler));
-  Expect.equals(NUMBER,
-                INTEGER.union(DOUBLE, compiler));
-  Expect.equals(NON_NULL,
-                INTEGER.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(NON_NULL,
-                INTEGER.union(STRING, compiler));
-  Expect.equals(NON_NULL,
-                INTEGER.union(READABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                INTEGER.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                INTEGER.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                INTEGER.union(nonPrimitive1, compiler));
-  Expect.equals(NON_NULL,
-                INTEGER.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                INTEGER.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                INTEGER.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                INTEGER.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER.union(STRING_OR_NULL, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                INTEGER.union(NULL, compiler));
-  Expect.equals(NON_NULL,
-                INTEGER.union(FIXED_ARRAY, compiler));
+  rule(NUMBER, NUMBER, NUMBER);
+  rule(NUMBER, INTEGER, NUMBER);
+  rule(NUMBER, DOUBLE, NUMBER);
+  rule(NUMBER, INDEXABLE_PRIMITIVE, NON_NULL);
+  rule(NUMBER, STRING, jsInterceptor);
+  rule(NUMBER, READABLE_ARRAY, jsInterceptor);
+  rule(NUMBER, MUTABLE_ARRAY, jsInterceptor);
+  rule(NUMBER, EXTENDABLE_ARRAY, jsInterceptor);
+  rule(NUMBER, nonPrimitive1, NON_NULL);
+  rule(NUMBER, nonPrimitive2, NON_NULL);
+  rule(NUMBER, potentialArray, UNKNOWN);
+  rule(NUMBER, potentialString, UNKNOWN);
+  rule(NUMBER, BOOLEAN_OR_NULL, jsInterceptorOrNull);
+  rule(NUMBER, NUMBER_OR_NULL, NUMBER_OR_NULL);
+  rule(NUMBER, INTEGER_OR_NULL, NUMBER_OR_NULL);
+  rule(NUMBER, DOUBLE_OR_NULL, NUMBER_OR_NULL);
+  rule(NUMBER, STRING_OR_NULL, jsInterceptorOrNull);
+  rule(NUMBER, NULL, NUMBER_OR_NULL);
+  rule(NUMBER, FIXED_ARRAY, jsInterceptor);
 
-  Expect.equals(DOUBLE,
-                DOUBLE.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE.union(UNKNOWN, compiler));
-  Expect.equals(NON_NULL,
-                DOUBLE.union(BOOLEAN, compiler));
-  Expect.equals(NUMBER,
-                DOUBLE.union(NUMBER, compiler));
-  Expect.equals(NUMBER,
-                DOUBLE.union(INTEGER, compiler));
-  Expect.equals(DOUBLE,
-                DOUBLE.union(DOUBLE, compiler));
-  Expect.equals(NON_NULL,
-                DOUBLE.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(NON_NULL,
-                DOUBLE.union(STRING, compiler));
-  Expect.equals(NON_NULL,
-                DOUBLE.union(READABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                DOUBLE.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                DOUBLE.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                DOUBLE.union(nonPrimitive1, compiler));
-  Expect.equals(NON_NULL,
-                DOUBLE.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                DOUBLE.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                DOUBLE.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                DOUBLE.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE.union(STRING_OR_NULL, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                DOUBLE.union(NULL, compiler));
-  Expect.equals(NON_NULL,
-                DOUBLE.union(FIXED_ARRAY, compiler));
+  rule(INTEGER, INTEGER, INTEGER);
+  rule(INTEGER, DOUBLE, NUMBER);
+  rule(INTEGER, INDEXABLE_PRIMITIVE, NON_NULL);
+  rule(INTEGER, STRING, jsInterceptor);
+  rule(INTEGER, READABLE_ARRAY, jsInterceptor);
+  rule(INTEGER, MUTABLE_ARRAY, jsInterceptor);
+  rule(INTEGER, EXTENDABLE_ARRAY, jsInterceptor);
+  rule(INTEGER, nonPrimitive1, NON_NULL);
+  rule(INTEGER, nonPrimitive2, NON_NULL);
+  rule(INTEGER, potentialArray, UNKNOWN);
+  rule(INTEGER, potentialString, UNKNOWN);
+  rule(INTEGER, BOOLEAN_OR_NULL, jsInterceptorOrNull);
+  rule(INTEGER, NUMBER_OR_NULL, NUMBER_OR_NULL);
+  rule(INTEGER, INTEGER_OR_NULL, INTEGER_OR_NULL);
+  rule(INTEGER, DOUBLE_OR_NULL, NUMBER_OR_NULL);
+  rule(INTEGER, STRING_OR_NULL, jsInterceptorOrNull);
+  rule(INTEGER, NULL, INTEGER_OR_NULL);
+  rule(INTEGER, FIXED_ARRAY, jsInterceptor);
 
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                INDEXABLE_PRIMITIVE.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                INDEXABLE_PRIMITIVE.union(UNKNOWN, compiler));
-  Expect.equals(NON_NULL,
-                INDEXABLE_PRIMITIVE.union(BOOLEAN, compiler));
-  Expect.equals(NON_NULL,
-                INDEXABLE_PRIMITIVE.union(NUMBER, compiler));
-  Expect.equals(NON_NULL,
-                INDEXABLE_PRIMITIVE.union(INTEGER, compiler));
-  Expect.equals(NON_NULL,
-                INDEXABLE_PRIMITIVE.union(DOUBLE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                INDEXABLE_PRIMITIVE.union(INDEXABLE_PRIMITIVE,
-                compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                INDEXABLE_PRIMITIVE.union(STRING, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                INDEXABLE_PRIMITIVE.union(READABLE_ARRAY, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                INDEXABLE_PRIMITIVE.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                INDEXABLE_PRIMITIVE.union(EXTENDABLE_ARRAY,
-                compiler));
-  Expect.equals(NON_NULL,
-                INDEXABLE_PRIMITIVE.union(nonPrimitive1, compiler));
-  Expect.equals(NON_NULL,
-                INDEXABLE_PRIMITIVE.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                INDEXABLE_PRIMITIVE.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                INDEXABLE_PRIMITIVE.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                INDEXABLE_PRIMITIVE.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                INDEXABLE_PRIMITIVE.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                INDEXABLE_PRIMITIVE.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                INDEXABLE_PRIMITIVE.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(jsIndexableOrNull,
-                INDEXABLE_PRIMITIVE.union(STRING_OR_NULL, compiler));
-  Expect.equals(jsIndexableOrNull,
-                INDEXABLE_PRIMITIVE.union(NULL, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                INDEXABLE_PRIMITIVE.union(FIXED_ARRAY, compiler));
+  rule(DOUBLE, DOUBLE, DOUBLE);
+  rule(DOUBLE, INDEXABLE_PRIMITIVE, NON_NULL);
+  rule(DOUBLE, STRING, jsInterceptor);
+  rule(DOUBLE, READABLE_ARRAY, jsInterceptor);
+  rule(DOUBLE, MUTABLE_ARRAY, jsInterceptor);
+  rule(DOUBLE, EXTENDABLE_ARRAY, jsInterceptor);
+  rule(DOUBLE, nonPrimitive1, NON_NULL);
+  rule(DOUBLE, nonPrimitive2, NON_NULL);
+  rule(DOUBLE, potentialArray, UNKNOWN);
+  rule(DOUBLE, potentialString, UNKNOWN);
+  rule(DOUBLE, BOOLEAN_OR_NULL, jsInterceptorOrNull);
+  rule(DOUBLE, NUMBER_OR_NULL, NUMBER_OR_NULL);
+  rule(DOUBLE, INTEGER_OR_NULL, NUMBER_OR_NULL);
+  rule(DOUBLE, DOUBLE_OR_NULL, DOUBLE_OR_NULL);
+  rule(DOUBLE, STRING_OR_NULL, jsInterceptorOrNull);
+  rule(DOUBLE, NULL, DOUBLE_OR_NULL);
+  rule(DOUBLE, FIXED_ARRAY, jsInterceptor);
 
-  Expect.equals(STRING,
-                STRING.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                STRING.union(UNKNOWN, compiler));
-  Expect.equals(NON_NULL,
-                STRING.union(BOOLEAN, compiler));
-  Expect.equals(NON_NULL,
-                STRING.union(NUMBER, compiler));
-  Expect.equals(NON_NULL,
-                STRING.union(INTEGER, compiler));
-  Expect.equals(NON_NULL,
-                STRING.union(DOUBLE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                STRING.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(STRING,
-                STRING.union(STRING, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                STRING.union(READABLE_ARRAY, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                STRING.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                STRING.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                STRING.union(nonPrimitive1, compiler));
-  Expect.equals(NON_NULL,
-                STRING.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                STRING.union(potentialArray, compiler));
-  Expect.equals(potentialString,
-                STRING.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                STRING.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                STRING.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                STRING.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                STRING.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(STRING_OR_NULL,
-                STRING.union(STRING_OR_NULL, compiler));
-  Expect.equals(STRING_OR_NULL,
-                STRING.union(NULL, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                STRING.union(FIXED_ARRAY, compiler));
+  rule(INDEXABLE_PRIMITIVE, INDEXABLE_PRIMITIVE, INDEXABLE_PRIMITIVE);
+  rule(INDEXABLE_PRIMITIVE, STRING, INDEXABLE_PRIMITIVE);
+  rule(INDEXABLE_PRIMITIVE, READABLE_ARRAY, INDEXABLE_PRIMITIVE);
+  rule(INDEXABLE_PRIMITIVE, MUTABLE_ARRAY, INDEXABLE_PRIMITIVE);
+  rule(INDEXABLE_PRIMITIVE, EXTENDABLE_ARRAY, INDEXABLE_PRIMITIVE);
+  rule(INDEXABLE_PRIMITIVE, nonPrimitive1, NON_NULL);
+  rule(INDEXABLE_PRIMITIVE, nonPrimitive2, NON_NULL);
+  rule(INDEXABLE_PRIMITIVE, potentialArray, UNKNOWN);
+  rule(INDEXABLE_PRIMITIVE, potentialString, UNKNOWN);
+  rule(INDEXABLE_PRIMITIVE, BOOLEAN_OR_NULL, UNKNOWN);
+  rule(INDEXABLE_PRIMITIVE, NUMBER_OR_NULL, UNKNOWN);
+  rule(INDEXABLE_PRIMITIVE, INTEGER_OR_NULL, UNKNOWN);
+  rule(INDEXABLE_PRIMITIVE, DOUBLE_OR_NULL, UNKNOWN);
+  rule(INDEXABLE_PRIMITIVE, STRING_OR_NULL, jsIndexableOrNull);
+  rule(INDEXABLE_PRIMITIVE, NULL, jsIndexableOrNull);
+  rule(INDEXABLE_PRIMITIVE, FIXED_ARRAY, INDEXABLE_PRIMITIVE);
 
-  Expect.equals(READABLE_ARRAY,
-                READABLE_ARRAY.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                READABLE_ARRAY.union(UNKNOWN, compiler));
-  Expect.equals(NON_NULL,
-                READABLE_ARRAY.union(BOOLEAN, compiler));
-  Expect.equals(NON_NULL,
-                READABLE_ARRAY.union(NUMBER, compiler));
-  Expect.equals(NON_NULL,
-                READABLE_ARRAY.union(INTEGER, compiler));
-  Expect.equals(NON_NULL,
-                READABLE_ARRAY.union(DOUBLE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                READABLE_ARRAY.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                READABLE_ARRAY.union(STRING, compiler));
-  Expect.equals(READABLE_ARRAY,
-                READABLE_ARRAY.union(READABLE_ARRAY, compiler));
-  Expect.equals(READABLE_ARRAY,
-                READABLE_ARRAY.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(READABLE_ARRAY,
-                READABLE_ARRAY.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                READABLE_ARRAY.union(nonPrimitive1, compiler));
-  Expect.equals(NON_NULL,
-                READABLE_ARRAY.union(nonPrimitive2, compiler));
-  Expect.equals(potentialArray,
-                READABLE_ARRAY.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                READABLE_ARRAY.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                READABLE_ARRAY.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                READABLE_ARRAY.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                READABLE_ARRAY.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                READABLE_ARRAY.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(jsIndexableOrNull,
-                READABLE_ARRAY.union(STRING_OR_NULL, compiler));
-  Expect.equals(jsArrayOrNull,
-                READABLE_ARRAY.union(NULL, compiler));
-  Expect.equals(READABLE_ARRAY,
-                READABLE_ARRAY.union(FIXED_ARRAY, compiler));
+  rule(STRING, STRING, STRING);
+  rule(STRING, READABLE_ARRAY, INDEXABLE_PRIMITIVE);
+  rule(STRING, MUTABLE_ARRAY, INDEXABLE_PRIMITIVE);
+  rule(STRING, EXTENDABLE_ARRAY, INDEXABLE_PRIMITIVE);
+  rule(STRING, nonPrimitive1, NON_NULL);
+  rule(STRING, nonPrimitive2, NON_NULL);
+  rule(STRING, potentialArray, UNKNOWN);
+  rule(STRING, potentialString, potentialString);
+  rule(STRING, BOOLEAN_OR_NULL, jsInterceptorOrNull);
+  rule(STRING, NUMBER_OR_NULL, jsInterceptorOrNull);
+  rule(STRING, INTEGER_OR_NULL, jsInterceptorOrNull);
+  rule(STRING, DOUBLE_OR_NULL, jsInterceptorOrNull);
+  rule(STRING, STRING_OR_NULL, STRING_OR_NULL);
+  rule(STRING, NULL, STRING_OR_NULL);
+  rule(STRING, FIXED_ARRAY, INDEXABLE_PRIMITIVE);
 
-  Expect.equals(MUTABLE_ARRAY,
-                MUTABLE_ARRAY.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                MUTABLE_ARRAY.union(UNKNOWN, compiler));
-  Expect.equals(NON_NULL,
-                MUTABLE_ARRAY.union(BOOLEAN, compiler));
-  Expect.equals(NON_NULL,
-                MUTABLE_ARRAY.union(NUMBER, compiler));
-  Expect.equals(NON_NULL,
-                MUTABLE_ARRAY.union(INTEGER, compiler));
-  Expect.equals(NON_NULL,
-                MUTABLE_ARRAY.union(DOUBLE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                MUTABLE_ARRAY.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                MUTABLE_ARRAY.union(STRING, compiler));
-  Expect.equals(READABLE_ARRAY,
-                MUTABLE_ARRAY.union(READABLE_ARRAY, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                MUTABLE_ARRAY.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                MUTABLE_ARRAY.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                MUTABLE_ARRAY.union(nonPrimitive1, compiler));
-  Expect.equals(NON_NULL,
-                MUTABLE_ARRAY.union(nonPrimitive2, compiler));
-  Expect.equals(potentialArray,MUTABLE_ARRAY.union(potentialArray,
-                compiler));
-  Expect.equals(UNKNOWN,
-                MUTABLE_ARRAY.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                MUTABLE_ARRAY.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                MUTABLE_ARRAY.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                MUTABLE_ARRAY.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                MUTABLE_ARRAY.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(jsIndexableOrNull,
-                MUTABLE_ARRAY.union(STRING_OR_NULL, compiler));
-  Expect.equals(jsMutableArrayOrNull,
-                MUTABLE_ARRAY.union(NULL, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                MUTABLE_ARRAY.union(FIXED_ARRAY, compiler));
+  rule(READABLE_ARRAY, READABLE_ARRAY, READABLE_ARRAY);
+  rule(READABLE_ARRAY, MUTABLE_ARRAY, READABLE_ARRAY);
+  rule(READABLE_ARRAY, EXTENDABLE_ARRAY, READABLE_ARRAY);
+  rule(READABLE_ARRAY, nonPrimitive1, NON_NULL);
+  rule(READABLE_ARRAY, nonPrimitive2, NON_NULL);
+  rule(READABLE_ARRAY, potentialArray, potentialArray);
+  rule(READABLE_ARRAY, potentialString, UNKNOWN);
+  rule(READABLE_ARRAY, BOOLEAN_OR_NULL, jsInterceptorOrNull);
+  rule(READABLE_ARRAY, NUMBER_OR_NULL, jsInterceptorOrNull);
+  rule(READABLE_ARRAY, INTEGER_OR_NULL, jsInterceptorOrNull);
+  rule(READABLE_ARRAY, DOUBLE_OR_NULL, jsInterceptorOrNull);
+  rule(READABLE_ARRAY, STRING_OR_NULL, jsIndexableOrNull);
+  rule(READABLE_ARRAY, NULL, jsArrayOrNull);
+  rule(READABLE_ARRAY, FIXED_ARRAY, READABLE_ARRAY);
 
-  Expect.equals(EXTENDABLE_ARRAY,
-                EXTENDABLE_ARRAY.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                EXTENDABLE_ARRAY.union(UNKNOWN, compiler));
-  Expect.equals(NON_NULL,
-                EXTENDABLE_ARRAY.union(BOOLEAN, compiler));
-  Expect.equals(NON_NULL,
-                EXTENDABLE_ARRAY.union(NUMBER, compiler));
-  Expect.equals(NON_NULL,
-                EXTENDABLE_ARRAY.union(INTEGER, compiler));
-  Expect.equals(NON_NULL,
-                EXTENDABLE_ARRAY.union(DOUBLE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                EXTENDABLE_ARRAY.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                EXTENDABLE_ARRAY.union(STRING, compiler));
-  Expect.equals(READABLE_ARRAY,
-                EXTENDABLE_ARRAY.union(READABLE_ARRAY, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                EXTENDABLE_ARRAY.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                EXTENDABLE_ARRAY.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                EXTENDABLE_ARRAY.union(nonPrimitive1, compiler));
-  Expect.equals(NON_NULL,
-                EXTENDABLE_ARRAY.union(nonPrimitive2, compiler));
-  Expect.equals(potentialArray,
-                EXTENDABLE_ARRAY.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                EXTENDABLE_ARRAY.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                EXTENDABLE_ARRAY.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                EXTENDABLE_ARRAY.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                EXTENDABLE_ARRAY.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                EXTENDABLE_ARRAY.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(jsIndexableOrNull,
-                EXTENDABLE_ARRAY.union(STRING_OR_NULL, compiler));
-  Expect.equals(jsExtendableArrayOrNull,
-                EXTENDABLE_ARRAY.union(NULL, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                EXTENDABLE_ARRAY.union(FIXED_ARRAY, compiler));
+  rule(MUTABLE_ARRAY, MUTABLE_ARRAY, MUTABLE_ARRAY);
+  rule(MUTABLE_ARRAY, EXTENDABLE_ARRAY, MUTABLE_ARRAY);
+  rule(MUTABLE_ARRAY, nonPrimitive1, NON_NULL);
+  rule(MUTABLE_ARRAY, nonPrimitive2, NON_NULL);
+  rule(MUTABLE_ARRAY, potentialArray, potentialArray);
+  rule(MUTABLE_ARRAY, potentialString, UNKNOWN);
+  rule(MUTABLE_ARRAY, BOOLEAN_OR_NULL, jsInterceptorOrNull);
+  rule(MUTABLE_ARRAY, NUMBER_OR_NULL, jsInterceptorOrNull);
+  rule(MUTABLE_ARRAY, INTEGER_OR_NULL, jsInterceptorOrNull);
+  rule(MUTABLE_ARRAY, DOUBLE_OR_NULL, jsInterceptorOrNull);
+  rule(MUTABLE_ARRAY, STRING_OR_NULL, jsIndexableOrNull);
+  rule(MUTABLE_ARRAY, NULL, jsMutableArrayOrNull);
+  rule(MUTABLE_ARRAY, FIXED_ARRAY, MUTABLE_ARRAY);
 
-  Expect.equals(nonPrimitive1,
-                nonPrimitive1.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive1.union(UNKNOWN, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive1.union(BOOLEAN, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive1.union(NUMBER, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive1.union(INTEGER, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive1.union(DOUBLE, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive1.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive1.union(STRING, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive1.union(READABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive1.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive1.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(nonPrimitive1,
-                nonPrimitive1.union(nonPrimitive1, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive1.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive1.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive1.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive1.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive1.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive1.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive1.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive1.union(STRING_OR_NULL, compiler));
-  Expect.isTrue(nonPrimitive1.union(NULL, compiler) is HBoundedType);
-  Expect.equals(NON_NULL,
-                nonPrimitive1.union(FIXED_ARRAY, compiler));
+  rule(EXTENDABLE_ARRAY, EXTENDABLE_ARRAY, EXTENDABLE_ARRAY);
+  rule(EXTENDABLE_ARRAY, nonPrimitive1, NON_NULL);
+  rule(EXTENDABLE_ARRAY, nonPrimitive2, NON_NULL);
+  rule(EXTENDABLE_ARRAY, potentialArray, potentialArray);
+  rule(EXTENDABLE_ARRAY, potentialString, UNKNOWN);
+  rule(EXTENDABLE_ARRAY, BOOLEAN_OR_NULL, jsInterceptorOrNull);
+  rule(EXTENDABLE_ARRAY, NUMBER_OR_NULL, jsInterceptorOrNull);
+  rule(EXTENDABLE_ARRAY, INTEGER_OR_NULL, jsInterceptorOrNull);
+  rule(EXTENDABLE_ARRAY, DOUBLE_OR_NULL, jsInterceptorOrNull);
+  rule(EXTENDABLE_ARRAY, STRING_OR_NULL, jsIndexableOrNull);
+  rule(EXTENDABLE_ARRAY, NULL, jsExtendableArrayOrNull);
+  rule(EXTENDABLE_ARRAY, FIXED_ARRAY, MUTABLE_ARRAY);
 
-  Expect.equals(nonPrimitive2,
-                nonPrimitive2.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive2.union(UNKNOWN, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive2.union(BOOLEAN, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive2.union(NUMBER, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive2.union(INTEGER, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive2.union(DOUBLE, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive2.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive2.union(STRING, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive2.union(READABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive2.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive2.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                nonPrimitive2.union(nonPrimitive1, compiler));
-  Expect.equals(nonPrimitive2,
-                nonPrimitive2.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive2.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive2.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive2.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive2.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive2.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive2.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                nonPrimitive2.union(STRING_OR_NULL, compiler));
-  Expect.isTrue(nonPrimitive2.union(NULL, compiler) is HBoundedType);
-  Expect.equals(NON_NULL,
-                nonPrimitive2.union(FIXED_ARRAY, compiler));
+  rule(nonPrimitive1, nonPrimitive1, nonPrimitive1);
+  rule(nonPrimitive1, nonPrimitive2, NON_NULL);
+  rule(nonPrimitive1, potentialArray, UNKNOWN);
+  rule(nonPrimitive1, potentialString, UNKNOWN);
+  rule(nonPrimitive1, BOOLEAN_OR_NULL, UNKNOWN);
+  rule(nonPrimitive1, NUMBER_OR_NULL, UNKNOWN);
+  rule(nonPrimitive1, INTEGER_OR_NULL, UNKNOWN);
+  rule(nonPrimitive1, DOUBLE_OR_NULL, UNKNOWN);
+  rule(nonPrimitive1, STRING_OR_NULL, UNKNOWN);
+  rule(nonPrimitive1, FIXED_ARRAY, NON_NULL);
 
-  Expect.equals(potentialArray,
-                potentialArray.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(UNKNOWN, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(BOOLEAN, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(NUMBER, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(INTEGER, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(DOUBLE, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(STRING, compiler));
-  Expect.equals(potentialArray,
-                potentialArray.union(READABLE_ARRAY, compiler));
-  Expect.equals(potentialArray,
-                potentialArray.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(potentialArray,
-                potentialArray.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(nonPrimitive1, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(nonPrimitive2, compiler));
-  Expect.equals(potentialArray,
-                potentialArray.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                potentialArray.union(STRING_OR_NULL, compiler));
-  Expect.equals(potentialArray,
-                potentialArray.union(NULL, compiler));
-  Expect.equals(potentialArray,
-                potentialArray.union(FIXED_ARRAY, compiler));
+  rule(nonPrimitive2, nonPrimitive2, nonPrimitive2);
+  rule(nonPrimitive2, potentialArray, UNKNOWN);
+  rule(nonPrimitive2, potentialString, UNKNOWN);
+  rule(nonPrimitive2, BOOLEAN_OR_NULL, UNKNOWN);
+  rule(nonPrimitive2, NUMBER_OR_NULL, UNKNOWN);
+  rule(nonPrimitive2, INTEGER_OR_NULL, UNKNOWN);
+  rule(nonPrimitive2, DOUBLE_OR_NULL, UNKNOWN);
+  rule(nonPrimitive2, STRING_OR_NULL, UNKNOWN);
+  rule(nonPrimitive2, FIXED_ARRAY, NON_NULL);
 
-  Expect.equals(potentialString,
-                potentialString.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(UNKNOWN, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(BOOLEAN, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(NUMBER, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(INTEGER, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(DOUBLE, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(potentialString,
-                potentialString.union(STRING, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(READABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(nonPrimitive1, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(potentialArray, compiler));
-  Expect.equals(potentialString,
-                potentialString.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(potentialString,
-                potentialString.union(STRING_OR_NULL, compiler));
-  Expect.equals(potentialString,
-                potentialString.union(NULL, compiler));
-  Expect.equals(UNKNOWN,
-                potentialString.union(FIXED_ARRAY, compiler));
+  rule(potentialArray, potentialArray, potentialArray);
+  rule(potentialArray, potentialString, UNKNOWN);
+  rule(potentialArray, BOOLEAN_OR_NULL, UNKNOWN);
+  rule(potentialArray, NUMBER_OR_NULL, UNKNOWN);
+  rule(potentialArray, INTEGER_OR_NULL, UNKNOWN);
+  rule(potentialArray, DOUBLE_OR_NULL, UNKNOWN);
+  rule(potentialArray, STRING_OR_NULL, UNKNOWN);
+  rule(potentialArray, NULL, potentialArray);
+  rule(potentialArray, FIXED_ARRAY, potentialArray);
 
-  Expect.equals(BOOLEAN_OR_NULL,
-                BOOLEAN_OR_NULL.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(UNKNOWN, compiler));
-  Expect.equals(BOOLEAN_OR_NULL,
-                BOOLEAN_OR_NULL.union(BOOLEAN, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(NUMBER, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(INTEGER, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(DOUBLE, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(STRING, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(READABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(nonPrimitive1, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(potentialString, compiler));
-  Expect.equals(BOOLEAN_OR_NULL,
-                BOOLEAN_OR_NULL.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(STRING_OR_NULL, compiler));
-  Expect.equals(BOOLEAN_OR_NULL,
-                BOOLEAN_OR_NULL.union(NULL, compiler));
-  Expect.equals(UNKNOWN,
-                BOOLEAN_OR_NULL.union(FIXED_ARRAY, compiler));
+  rule(potentialString, potentialString, potentialString);
+  rule(potentialString, BOOLEAN_OR_NULL, UNKNOWN);
+  rule(potentialString, NUMBER_OR_NULL, UNKNOWN);
+  rule(potentialString, INTEGER_OR_NULL, UNKNOWN);
+  rule(potentialString, DOUBLE_OR_NULL, UNKNOWN);
+  rule(potentialString, STRING_OR_NULL, potentialString);
+  rule(potentialString, NULL, potentialString);
+  rule(potentialString, FIXED_ARRAY, UNKNOWN);
 
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER_OR_NULL.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(UNKNOWN, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(BOOLEAN, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER_OR_NULL.union(NUMBER, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER_OR_NULL.union(INTEGER, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER_OR_NULL.union(DOUBLE, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(STRING, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(READABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(nonPrimitive1, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER_OR_NULL.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER_OR_NULL.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER_OR_NULL.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(STRING_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER_OR_NULL.union(NULL, compiler));
-  Expect.equals(UNKNOWN,
-                NUMBER_OR_NULL.union(FIXED_ARRAY, compiler));
+  rule(BOOLEAN_OR_NULL, BOOLEAN_OR_NULL, BOOLEAN_OR_NULL);
+  rule(BOOLEAN_OR_NULL, NUMBER_OR_NULL, jsInterceptorOrNull);
+  rule(BOOLEAN_OR_NULL, INTEGER_OR_NULL, jsInterceptorOrNull);
+  rule(BOOLEAN_OR_NULL, DOUBLE_OR_NULL, jsInterceptorOrNull);
+  rule(BOOLEAN_OR_NULL, STRING_OR_NULL, jsInterceptorOrNull);
+  rule(BOOLEAN_OR_NULL, NULL, BOOLEAN_OR_NULL);
+  rule(BOOLEAN_OR_NULL, FIXED_ARRAY, jsInterceptorOrNull);
 
-  Expect.equals(INTEGER_OR_NULL,
-                INTEGER_OR_NULL.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(UNKNOWN, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(BOOLEAN, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                INTEGER_OR_NULL.union(NUMBER, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                INTEGER_OR_NULL.union(INTEGER, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                INTEGER_OR_NULL.union(DOUBLE, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(STRING, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(READABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(nonPrimitive1, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                INTEGER_OR_NULL.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                INTEGER_OR_NULL.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                INTEGER_OR_NULL.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(STRING_OR_NULL, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                INTEGER_OR_NULL.union(NULL, compiler));
-  Expect.equals(UNKNOWN,
-                INTEGER_OR_NULL.union(FIXED_ARRAY, compiler));
+  rule(NUMBER_OR_NULL, NUMBER_OR_NULL, NUMBER_OR_NULL);
+  rule(NUMBER_OR_NULL, INTEGER_OR_NULL, NUMBER_OR_NULL);
+  rule(NUMBER_OR_NULL, DOUBLE_OR_NULL, NUMBER_OR_NULL);
+  rule(NUMBER_OR_NULL, STRING_OR_NULL, jsInterceptorOrNull);
+  rule(NUMBER_OR_NULL, NULL, NUMBER_OR_NULL);
+  rule(NUMBER_OR_NULL, FIXED_ARRAY, jsInterceptorOrNull);
 
-  Expect.equals(DOUBLE_OR_NULL,
-                DOUBLE_OR_NULL.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(UNKNOWN, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(BOOLEAN, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                DOUBLE_OR_NULL.union(NUMBER, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                DOUBLE_OR_NULL.union(INTEGER, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                DOUBLE_OR_NULL.union(DOUBLE, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(STRING, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(READABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(nonPrimitive1, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                DOUBLE_OR_NULL.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                DOUBLE_OR_NULL.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                DOUBLE_OR_NULL.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(STRING_OR_NULL, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                DOUBLE_OR_NULL.union(NULL, compiler));
-  Expect.equals(UNKNOWN,
-                DOUBLE_OR_NULL.union(FIXED_ARRAY, compiler));
+  rule(INTEGER_OR_NULL, INTEGER_OR_NULL, INTEGER_OR_NULL);
+  rule(INTEGER_OR_NULL, DOUBLE_OR_NULL, NUMBER_OR_NULL);
+  rule(INTEGER_OR_NULL, STRING_OR_NULL, jsInterceptorOrNull);
+  rule(INTEGER_OR_NULL, NULL, INTEGER_OR_NULL);
+  rule(INTEGER_OR_NULL, FIXED_ARRAY, jsInterceptorOrNull);
 
-  Expect.equals(STRING_OR_NULL,
-                STRING_OR_NULL.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(UNKNOWN, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(BOOLEAN, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(NUMBER, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(INTEGER, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(DOUBLE, compiler));
-  Expect.equals(jsIndexableOrNull,
-                STRING_OR_NULL.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(STRING_OR_NULL,
-                STRING_OR_NULL.union(STRING, compiler));
-  Expect.equals(jsIndexableOrNull,
-                STRING_OR_NULL.union(READABLE_ARRAY, compiler));
-  Expect.equals(jsIndexableOrNull,
-                STRING_OR_NULL.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(jsIndexableOrNull,
-                STRING_OR_NULL.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(nonPrimitive1, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(nonPrimitive2, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(potentialArray, compiler));
-  Expect.equals(potentialString,
-                STRING_OR_NULL.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                STRING_OR_NULL.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(STRING_OR_NULL,
-                STRING_OR_NULL.union(STRING_OR_NULL, compiler));
-  Expect.equals(STRING_OR_NULL,
-                STRING_OR_NULL.union(NULL, compiler));
-  Expect.equals(jsIndexableOrNull,
-                STRING_OR_NULL.union(FIXED_ARRAY, compiler));
+  rule(DOUBLE_OR_NULL, DOUBLE_OR_NULL, DOUBLE_OR_NULL);
+  rule(DOUBLE_OR_NULL, STRING_OR_NULL, jsInterceptorOrNull);
+  rule(DOUBLE_OR_NULL, NULL, DOUBLE_OR_NULL);
+  rule(DOUBLE_OR_NULL, FIXED_ARRAY, jsInterceptorOrNull);
 
-  Expect.equals(NULL,
-                NULL.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                NULL.union(UNKNOWN, compiler));
-  Expect.equals(BOOLEAN_OR_NULL,
-                NULL.union(BOOLEAN, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NULL.union(NUMBER, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                NULL.union(INTEGER, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                NULL.union(DOUBLE, compiler));
-  Expect.equals(jsIndexableOrNull,
-                NULL.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(STRING_OR_NULL,
-                NULL.union(STRING, compiler));
-  Expect.equals(jsArrayOrNull,
-                NULL.union(READABLE_ARRAY, compiler));
-  Expect.equals(jsMutableArrayOrNull,
-                NULL.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(jsExtendableArrayOrNull,
-                NULL.union(EXTENDABLE_ARRAY, compiler));
-  Expect.isTrue(NULL.union(nonPrimitive1, compiler).canBeNull());
-  Expect.isTrue(NULL.union(nonPrimitive2, compiler).canBeNull());
-  Expect.equals(potentialArray,
-                NULL.union(potentialArray, compiler));
-  Expect.equals(potentialString,
-                NULL.union(potentialString, compiler));
-  Expect.equals(BOOLEAN_OR_NULL,
-                NULL.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NULL.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                NULL.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                NULL.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(STRING_OR_NULL,
-                NULL.union(STRING_OR_NULL, compiler));
-  Expect.equals(NULL,
-                NULL.union(NULL, compiler));
-  Expect.equals(jsFixedArrayOrNull,
-                NULL.union(FIXED_ARRAY, compiler));
+  rule(STRING_OR_NULL, STRING_OR_NULL, STRING_OR_NULL);
+  rule(STRING_OR_NULL, NULL, STRING_OR_NULL);
+  rule(STRING_OR_NULL, FIXED_ARRAY, jsIndexableOrNull);
 
-  Expect.equals(FIXED_ARRAY,
-                FIXED_ARRAY.union(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                FIXED_ARRAY.union(UNKNOWN, compiler));
-  Expect.equals(NON_NULL,
-                FIXED_ARRAY.union(BOOLEAN, compiler));
-  Expect.equals(NON_NULL,
-                FIXED_ARRAY.union(NUMBER, compiler));
-  Expect.equals(NON_NULL,
-                FIXED_ARRAY.union(INTEGER, compiler));
-  Expect.equals(NON_NULL,
-                FIXED_ARRAY.union(DOUBLE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                FIXED_ARRAY.union(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                FIXED_ARRAY.union(STRING, compiler));
-  Expect.equals(READABLE_ARRAY,
-                FIXED_ARRAY.union(READABLE_ARRAY, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                FIXED_ARRAY.union(MUTABLE_ARRAY, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                FIXED_ARRAY.union(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(NON_NULL,
-                FIXED_ARRAY.union(nonPrimitive1, compiler));
-  Expect.equals(NON_NULL,
-                FIXED_ARRAY.union(nonPrimitive2, compiler));
-  Expect.equals(potentialArray,
-                FIXED_ARRAY.union(potentialArray, compiler));
-  Expect.equals(UNKNOWN,
-                FIXED_ARRAY.union(potentialString, compiler));
-  Expect.equals(UNKNOWN,
-                FIXED_ARRAY.union(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                FIXED_ARRAY.union(NUMBER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                FIXED_ARRAY.union(INTEGER_OR_NULL, compiler));
-  Expect.equals(UNKNOWN,
-                FIXED_ARRAY.union(DOUBLE_OR_NULL, compiler));
-  Expect.equals(jsIndexableOrNull,
-                FIXED_ARRAY.union(STRING_OR_NULL, compiler));
-  Expect.equals(jsFixedArrayOrNull,
-                FIXED_ARRAY.union(NULL, compiler));
-  Expect.equals(FIXED_ARRAY,
-                FIXED_ARRAY.union(FIXED_ARRAY, compiler));
+  rule(NULL, NULL, NULL);
+  rule(NULL, FIXED_ARRAY, jsFixedArrayOrNull);
+
+  rule(FIXED_ARRAY, FIXED_ARRAY, FIXED_ARRAY);
+
+  check(nonPrimitive1, NULL, (type) => type is HBoundedType);
+  check(nonPrimitive2, NULL, (type) => type is HBoundedType);
+  check(NULL, nonPrimitive1, (type) => type.canBeNull());
+  check(NULL, nonPrimitive2, (type) => type.canBeNull());
+
+  ruleSet.validateCoverage();
 }
 
 void testIntersection(MockCompiler compiler) {
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(CONFLICTING, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(nonPrimitive2, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(potentialArray, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(potentialString, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                CONFLICTING.intersection(FIXED_ARRAY, compiler));
+  RuleSet ruleSet = new RuleSet('intersection',
+                                (t1, t2) => t1.intersection(t2, compiler));
+  rule(type1, type2, result) => ruleSet.rule(type1, type2, result);
 
-  Expect.equals(CONFLICTING,
-                UNKNOWN.intersection(CONFLICTING, compiler));
-  Expect.equals(UNKNOWN,
-                UNKNOWN.intersection(UNKNOWN, compiler));
-  Expect.equals(BOOLEAN,
-                UNKNOWN.intersection(BOOLEAN, compiler));
-  Expect.equals(NUMBER,
-                UNKNOWN.intersection(NUMBER, compiler));
-  Expect.equals(INTEGER,
-                UNKNOWN.intersection(INTEGER, compiler));
-  Expect.equals(DOUBLE,
-                UNKNOWN.intersection(DOUBLE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                UNKNOWN.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(STRING,
-                UNKNOWN.intersection(STRING, compiler));
-  Expect.equals(READABLE_ARRAY,
-                UNKNOWN.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                UNKNOWN.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                UNKNOWN.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(nonPrimitive1,
-                UNKNOWN.intersection(nonPrimitive1, compiler));
-  Expect.equals(nonPrimitive2,
-                UNKNOWN.intersection(nonPrimitive2, compiler));
-  Expect.equals(potentialArray,
-                UNKNOWN.intersection(potentialArray, compiler));
-  Expect.equals(potentialString,
-                UNKNOWN.intersection(potentialString, compiler));
-  Expect.equals(BOOLEAN_OR_NULL,
-                UNKNOWN.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                UNKNOWN.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                UNKNOWN.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                UNKNOWN.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(STRING_OR_NULL,
-                UNKNOWN.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(NULL,
-                UNKNOWN.intersection(NULL, compiler));
-  Expect.equals(FIXED_ARRAY,
-                UNKNOWN.intersection(FIXED_ARRAY, compiler));
+  rule(CONFLICTING, CONFLICTING, CONFLICTING);
+  rule(CONFLICTING, UNKNOWN, CONFLICTING);
+  rule(CONFLICTING, BOOLEAN, CONFLICTING);
+  rule(CONFLICTING, NUMBER, CONFLICTING);
+  rule(CONFLICTING, INTEGER, CONFLICTING);
+  rule(CONFLICTING, DOUBLE, CONFLICTING);
+  rule(CONFLICTING, INDEXABLE_PRIMITIVE, CONFLICTING);
+  rule(CONFLICTING, STRING, CONFLICTING);
+  rule(CONFLICTING, READABLE_ARRAY, CONFLICTING);
+  rule(CONFLICTING, MUTABLE_ARRAY, CONFLICTING);
+  rule(CONFLICTING, EXTENDABLE_ARRAY, CONFLICTING);
+  rule(CONFLICTING, nonPrimitive1, CONFLICTING);
+  rule(CONFLICTING, nonPrimitive2, CONFLICTING);
+  rule(CONFLICTING, potentialArray, CONFLICTING);
+  rule(CONFLICTING, potentialString, CONFLICTING);
+  rule(CONFLICTING, BOOLEAN_OR_NULL, CONFLICTING);
+  rule(CONFLICTING, NUMBER_OR_NULL, CONFLICTING);
+  rule(CONFLICTING, INTEGER_OR_NULL, CONFLICTING);
+  rule(CONFLICTING, DOUBLE_OR_NULL, CONFLICTING);
+  rule(CONFLICTING, STRING_OR_NULL, CONFLICTING);
+  rule(CONFLICTING, NULL, CONFLICTING);
+  rule(CONFLICTING, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(CONFLICTING, compiler));
-  Expect.equals(BOOLEAN,
-                BOOLEAN.intersection(UNKNOWN, compiler));
-  Expect.equals(BOOLEAN,
-                BOOLEAN.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(nonPrimitive2, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(potentialArray, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(potentialString, compiler));
-  Expect.equals(BOOLEAN,
-                BOOLEAN.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN.intersection(FIXED_ARRAY, compiler));
+  rule(UNKNOWN, UNKNOWN, UNKNOWN);
+  rule(UNKNOWN, BOOLEAN, BOOLEAN);
+  rule(UNKNOWN, NUMBER, NUMBER);
+  rule(UNKNOWN, INTEGER, INTEGER);
+  rule(UNKNOWN, DOUBLE, DOUBLE);
+  rule(UNKNOWN, INDEXABLE_PRIMITIVE, INDEXABLE_PRIMITIVE);
+  rule(UNKNOWN, STRING, STRING);
+  rule(UNKNOWN, READABLE_ARRAY, READABLE_ARRAY);
+  rule(UNKNOWN, MUTABLE_ARRAY, MUTABLE_ARRAY);
+  rule(UNKNOWN, EXTENDABLE_ARRAY, EXTENDABLE_ARRAY);
+  rule(UNKNOWN, nonPrimitive1, nonPrimitive1);
+  rule(UNKNOWN, nonPrimitive2, nonPrimitive2);
+  rule(UNKNOWN, potentialArray, potentialArray);
+  rule(UNKNOWN, potentialString, potentialString);
+  rule(UNKNOWN, BOOLEAN_OR_NULL, BOOLEAN_OR_NULL);
+  rule(UNKNOWN, NUMBER_OR_NULL, NUMBER_OR_NULL);
+  rule(UNKNOWN, INTEGER_OR_NULL, INTEGER_OR_NULL);
+  rule(UNKNOWN, DOUBLE_OR_NULL, DOUBLE_OR_NULL);
+  rule(UNKNOWN, STRING_OR_NULL, STRING_OR_NULL);
+  rule(UNKNOWN, NULL, NULL);
+  rule(UNKNOWN, FIXED_ARRAY, FIXED_ARRAY);
 
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(CONFLICTING, compiler));
-  Expect.equals(NUMBER,
-                NUMBER.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(BOOLEAN, compiler));
-  Expect.equals(NUMBER,
-                NUMBER.intersection(NUMBER, compiler));
-  Expect.equals(INTEGER,
-                NUMBER.intersection(INTEGER, compiler));
-  Expect.equals(DOUBLE,
-                NUMBER.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(nonPrimitive2, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(potentialArray, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(potentialString, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NUMBER,
-                NUMBER.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(INTEGER,
-                NUMBER.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(DOUBLE,
-                NUMBER.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER.intersection(FIXED_ARRAY, compiler));
+  rule(BOOLEAN, BOOLEAN, BOOLEAN);
+  rule(BOOLEAN, NUMBER, CONFLICTING);
+  rule(BOOLEAN, INTEGER, CONFLICTING);
+  rule(BOOLEAN, DOUBLE, CONFLICTING);
+  rule(BOOLEAN, INDEXABLE_PRIMITIVE, CONFLICTING);
+  rule(BOOLEAN, STRING, CONFLICTING);
+  rule(BOOLEAN, READABLE_ARRAY, CONFLICTING);
+  rule(BOOLEAN, MUTABLE_ARRAY, CONFLICTING);
+  rule(BOOLEAN, EXTENDABLE_ARRAY, CONFLICTING);
+  rule(BOOLEAN, nonPrimitive1, CONFLICTING);
+  rule(BOOLEAN, nonPrimitive2, CONFLICTING);
+  rule(BOOLEAN, potentialArray, CONFLICTING);
+  rule(BOOLEAN, potentialString, CONFLICTING);
+  rule(BOOLEAN, BOOLEAN_OR_NULL, BOOLEAN);
+  rule(BOOLEAN, NUMBER_OR_NULL, CONFLICTING);
+  rule(BOOLEAN, INTEGER_OR_NULL, CONFLICTING);
+  rule(BOOLEAN, DOUBLE_OR_NULL, CONFLICTING);
+  rule(BOOLEAN, STRING_OR_NULL, CONFLICTING);
+  rule(BOOLEAN, NULL, CONFLICTING);
+  rule(BOOLEAN, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(CONFLICTING, compiler));
-  Expect.equals(INTEGER,
-                INTEGER.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(BOOLEAN, compiler));
-  Expect.equals(INTEGER,
-                INTEGER.intersection(NUMBER, compiler));
-  Expect.equals(INTEGER,
-                INTEGER.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(nonPrimitive2, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(potentialArray, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(potentialString, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(INTEGER,
-                INTEGER.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(INTEGER,
-                INTEGER.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER.intersection(FIXED_ARRAY, compiler));
+  rule(NUMBER, NUMBER, NUMBER);
+  rule(NUMBER, INTEGER, INTEGER);
+  rule(NUMBER, DOUBLE, DOUBLE);
+  rule(NUMBER, INDEXABLE_PRIMITIVE, CONFLICTING);
+  rule(NUMBER, STRING, CONFLICTING);
+  rule(NUMBER, READABLE_ARRAY, CONFLICTING);
+  rule(NUMBER, MUTABLE_ARRAY, CONFLICTING);
+  rule(NUMBER, EXTENDABLE_ARRAY, CONFLICTING);
+  rule(NUMBER, nonPrimitive1, CONFLICTING);
+  rule(NUMBER, nonPrimitive2, CONFLICTING);
+  rule(NUMBER, potentialArray, CONFLICTING);
+  rule(NUMBER, potentialString, CONFLICTING);
+  rule(NUMBER, BOOLEAN_OR_NULL, CONFLICTING);
+  rule(NUMBER, NUMBER_OR_NULL, NUMBER);
+  rule(NUMBER, INTEGER_OR_NULL, INTEGER);
+  rule(NUMBER, DOUBLE_OR_NULL, DOUBLE);
+  rule(NUMBER, STRING_OR_NULL, CONFLICTING);
+  rule(NUMBER, NULL, CONFLICTING);
+  rule(NUMBER, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(CONFLICTING, compiler));
-  Expect.equals(DOUBLE,
-                DOUBLE.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(BOOLEAN, compiler));
-  Expect.equals(DOUBLE,
-                DOUBLE.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(INTEGER, compiler));
-  Expect.equals(DOUBLE,
-                DOUBLE.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(nonPrimitive2, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(potentialArray, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(potentialString, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(DOUBLE,
-                DOUBLE.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(DOUBLE,
-                DOUBLE.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE.intersection(FIXED_ARRAY, compiler));
+  rule(INTEGER, INTEGER, INTEGER);
+  rule(INTEGER, DOUBLE, CONFLICTING);
+  rule(INTEGER, INDEXABLE_PRIMITIVE, CONFLICTING);
+  rule(INTEGER, STRING, CONFLICTING);
+  rule(INTEGER, READABLE_ARRAY, CONFLICTING);
+  rule(INTEGER, MUTABLE_ARRAY, CONFLICTING);
+  rule(INTEGER, EXTENDABLE_ARRAY, CONFLICTING);
+  rule(INTEGER, nonPrimitive1, CONFLICTING);
+  rule(INTEGER, nonPrimitive2, CONFLICTING);
+  rule(INTEGER, potentialArray, CONFLICTING);
+  rule(INTEGER, potentialString, CONFLICTING);
+  rule(INTEGER, BOOLEAN_OR_NULL, CONFLICTING);
+  rule(INTEGER, NUMBER_OR_NULL, INTEGER);
+  rule(INTEGER, INTEGER_OR_NULL, INTEGER);
+  rule(INTEGER, DOUBLE_OR_NULL, CONFLICTING);
+  rule(INTEGER, STRING_OR_NULL, CONFLICTING);
+  rule(INTEGER, NULL, CONFLICTING);
+  rule(INTEGER, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(CONFLICTING, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                INDEXABLE_PRIMITIVE.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(DOUBLE, compiler));
-  Expect.equals(INDEXABLE_PRIMITIVE,
-                INDEXABLE_PRIMITIVE.intersection(INDEXABLE_PRIMITIVE,
-                compiler));
-  Expect.equals(STRING,
-                INDEXABLE_PRIMITIVE.intersection(STRING, compiler));
-  Expect.equals(READABLE_ARRAY,
-                INDEXABLE_PRIMITIVE.intersection(READABLE_ARRAY,
-                compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                INDEXABLE_PRIMITIVE.intersection(MUTABLE_ARRAY,
-                compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                INDEXABLE_PRIMITIVE.intersection(EXTENDABLE_ARRAY,
-                compiler));
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(nonPrimitive2, compiler));
-  Expect.equals(READABLE_ARRAY,
-                INDEXABLE_PRIMITIVE.intersection(potentialArray,
-                compiler));
-  Expect.equals(STRING,
-                INDEXABLE_PRIMITIVE.intersection(potentialString,
-                compiler));
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(STRING,
-                INDEXABLE_PRIMITIVE.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                INDEXABLE_PRIMITIVE.intersection(NULL, compiler));
-  Expect.equals(FIXED_ARRAY,
-                INDEXABLE_PRIMITIVE.intersection(FIXED_ARRAY, compiler));
+  rule(DOUBLE, DOUBLE, DOUBLE);
+  rule(DOUBLE, INDEXABLE_PRIMITIVE, CONFLICTING);
+  rule(DOUBLE, STRING, CONFLICTING);
+  rule(DOUBLE, READABLE_ARRAY, CONFLICTING);
+  rule(DOUBLE, MUTABLE_ARRAY, CONFLICTING);
+  rule(DOUBLE, EXTENDABLE_ARRAY, CONFLICTING);
+  rule(DOUBLE, nonPrimitive1, CONFLICTING);
+  rule(DOUBLE, nonPrimitive2, CONFLICTING);
+  rule(DOUBLE, potentialArray, CONFLICTING);
+  rule(DOUBLE, potentialString, CONFLICTING);
+  rule(DOUBLE, BOOLEAN_OR_NULL, CONFLICTING);
+  rule(DOUBLE, NUMBER_OR_NULL, DOUBLE);
+  rule(DOUBLE, INTEGER_OR_NULL, CONFLICTING);
+  rule(DOUBLE, DOUBLE_OR_NULL, DOUBLE);
+  rule(DOUBLE, STRING_OR_NULL, CONFLICTING);
+  rule(DOUBLE, NULL, CONFLICTING);
+  rule(DOUBLE, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                STRING.intersection(CONFLICTING, compiler));
-  Expect.equals(STRING,
-                STRING.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(DOUBLE, compiler));
-  Expect.equals(STRING,
-                STRING.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(STRING,
-                STRING.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(nonPrimitive2, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(potentialArray, compiler));
-  Expect.equals(STRING,
-                STRING.intersection(potentialString, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(STRING,
-                STRING.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                STRING.intersection(FIXED_ARRAY, compiler));
+  rule(INDEXABLE_PRIMITIVE, INDEXABLE_PRIMITIVE, INDEXABLE_PRIMITIVE);
+  rule(INDEXABLE_PRIMITIVE, STRING, STRING);
+  rule(INDEXABLE_PRIMITIVE, READABLE_ARRAY, READABLE_ARRAY);
+  rule(INDEXABLE_PRIMITIVE, MUTABLE_ARRAY, MUTABLE_ARRAY);
+  rule(INDEXABLE_PRIMITIVE, EXTENDABLE_ARRAY, EXTENDABLE_ARRAY);
+  rule(INDEXABLE_PRIMITIVE, nonPrimitive1, CONFLICTING);
+  rule(INDEXABLE_PRIMITIVE, nonPrimitive2, CONFLICTING);
+  rule(INDEXABLE_PRIMITIVE, potentialArray, READABLE_ARRAY);
+  rule(INDEXABLE_PRIMITIVE, potentialString, STRING);
+  rule(INDEXABLE_PRIMITIVE, BOOLEAN_OR_NULL, CONFLICTING);
+  rule(INDEXABLE_PRIMITIVE, NUMBER_OR_NULL, CONFLICTING);
+  rule(INDEXABLE_PRIMITIVE, INTEGER_OR_NULL, CONFLICTING);
+  rule(INDEXABLE_PRIMITIVE, DOUBLE_OR_NULL, CONFLICTING);
+  rule(INDEXABLE_PRIMITIVE, STRING_OR_NULL, STRING);
+  rule(INDEXABLE_PRIMITIVE, NULL, CONFLICTING);
+  rule(INDEXABLE_PRIMITIVE, FIXED_ARRAY, FIXED_ARRAY);
 
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(CONFLICTING, compiler));
-  Expect.equals(READABLE_ARRAY,
-                READABLE_ARRAY.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(DOUBLE, compiler));
-  Expect.equals(READABLE_ARRAY,
-                READABLE_ARRAY.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(STRING, compiler));
-  Expect.equals(READABLE_ARRAY,
-                READABLE_ARRAY.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                READABLE_ARRAY.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                READABLE_ARRAY.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(nonPrimitive2, compiler));
-  Expect.equals(READABLE_ARRAY,
-                READABLE_ARRAY.intersection(potentialArray, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(potentialString, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                READABLE_ARRAY.intersection(NULL, compiler));
-  Expect.equals(FIXED_ARRAY,
-                READABLE_ARRAY.intersection(FIXED_ARRAY, compiler));
+  rule(STRING, STRING, STRING);
+  rule(STRING, READABLE_ARRAY, CONFLICTING);
+  rule(STRING, MUTABLE_ARRAY, CONFLICTING);
+  rule(STRING, EXTENDABLE_ARRAY, CONFLICTING);
+  rule(STRING, nonPrimitive1, CONFLICTING);
+  rule(STRING, nonPrimitive2, CONFLICTING);
+  rule(STRING, potentialArray, CONFLICTING);
+  rule(STRING, potentialString, STRING);
+  rule(STRING, BOOLEAN_OR_NULL, CONFLICTING);
+  rule(STRING, NUMBER_OR_NULL, CONFLICTING);
+  rule(STRING, INTEGER_OR_NULL, CONFLICTING);
+  rule(STRING, DOUBLE_OR_NULL, CONFLICTING);
+  rule(STRING, STRING_OR_NULL, STRING);
+  rule(STRING, NULL, CONFLICTING);
+  rule(STRING, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(CONFLICTING, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                MUTABLE_ARRAY.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(DOUBLE, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                MUTABLE_ARRAY.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(STRING, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                MUTABLE_ARRAY.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                MUTABLE_ARRAY.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                MUTABLE_ARRAY.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(nonPrimitive2, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                MUTABLE_ARRAY.intersection(potentialArray, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(potentialString, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                MUTABLE_ARRAY.intersection(NULL, compiler));
-  Expect.equals(FIXED_ARRAY,
-                MUTABLE_ARRAY.intersection(FIXED_ARRAY, compiler));
+  rule(READABLE_ARRAY, READABLE_ARRAY, READABLE_ARRAY);
+  rule(READABLE_ARRAY, MUTABLE_ARRAY, MUTABLE_ARRAY);
+  rule(READABLE_ARRAY, EXTENDABLE_ARRAY, EXTENDABLE_ARRAY);
+  rule(READABLE_ARRAY, nonPrimitive1, CONFLICTING);
+  rule(READABLE_ARRAY, nonPrimitive2, CONFLICTING);
+  rule(READABLE_ARRAY, potentialArray, READABLE_ARRAY);
+  rule(READABLE_ARRAY, potentialString, CONFLICTING);
+  rule(READABLE_ARRAY, BOOLEAN_OR_NULL, CONFLICTING);
+  rule(READABLE_ARRAY, NUMBER_OR_NULL, CONFLICTING);
+  rule(READABLE_ARRAY, INTEGER_OR_NULL, CONFLICTING);
+  rule(READABLE_ARRAY, DOUBLE_OR_NULL, CONFLICTING);
+  rule(READABLE_ARRAY, STRING_OR_NULL, CONFLICTING);
+  rule(READABLE_ARRAY, NULL, CONFLICTING);
+  rule(READABLE_ARRAY, FIXED_ARRAY, FIXED_ARRAY);
 
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(CONFLICTING, compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                EXTENDABLE_ARRAY.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(DOUBLE, compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                EXTENDABLE_ARRAY.intersection(INDEXABLE_PRIMITIVE,
-                compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(STRING, compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                EXTENDABLE_ARRAY.intersection(READABLE_ARRAY,
-                compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                EXTENDABLE_ARRAY.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                EXTENDABLE_ARRAY.intersection(EXTENDABLE_ARRAY,
-                compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(nonPrimitive2, compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                EXTENDABLE_ARRAY.intersection(potentialArray,
-                compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(potentialString, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                EXTENDABLE_ARRAY.intersection(FIXED_ARRAY, compiler));
+  rule(MUTABLE_ARRAY, MUTABLE_ARRAY, MUTABLE_ARRAY);
+  rule(MUTABLE_ARRAY, EXTENDABLE_ARRAY, EXTENDABLE_ARRAY);
+  rule(MUTABLE_ARRAY, nonPrimitive1, CONFLICTING);
+  rule(MUTABLE_ARRAY, nonPrimitive2, CONFLICTING);
+  rule(MUTABLE_ARRAY, potentialArray, MUTABLE_ARRAY);
+  rule(MUTABLE_ARRAY, potentialString, CONFLICTING);
+  rule(MUTABLE_ARRAY, BOOLEAN_OR_NULL, CONFLICTING);
+  rule(MUTABLE_ARRAY, NUMBER_OR_NULL, CONFLICTING);
+  rule(MUTABLE_ARRAY, INTEGER_OR_NULL, CONFLICTING);
+  rule(MUTABLE_ARRAY, DOUBLE_OR_NULL, CONFLICTING);
+  rule(MUTABLE_ARRAY, STRING_OR_NULL, CONFLICTING);
+  rule(MUTABLE_ARRAY, NULL, CONFLICTING);
+  rule(MUTABLE_ARRAY, FIXED_ARRAY, FIXED_ARRAY);
 
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(CONFLICTING, compiler));
-  Expect.equals(nonPrimitive1,
-                nonPrimitive1.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(nonPrimitive1,
-                nonPrimitive1.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(nonPrimitive2, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(potentialArray, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(potentialString, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive1.intersection(FIXED_ARRAY, compiler));
+  rule(EXTENDABLE_ARRAY, EXTENDABLE_ARRAY, EXTENDABLE_ARRAY);
+  rule(EXTENDABLE_ARRAY, nonPrimitive1, CONFLICTING);
+  rule(EXTENDABLE_ARRAY, nonPrimitive2, CONFLICTING);
+  rule(EXTENDABLE_ARRAY, potentialArray, EXTENDABLE_ARRAY);
+  rule(EXTENDABLE_ARRAY, potentialString, CONFLICTING);
+  rule(EXTENDABLE_ARRAY, BOOLEAN_OR_NULL, CONFLICTING);
+  rule(EXTENDABLE_ARRAY, NUMBER_OR_NULL, CONFLICTING);
+  rule(EXTENDABLE_ARRAY, INTEGER_OR_NULL, CONFLICTING);
+  rule(EXTENDABLE_ARRAY, DOUBLE_OR_NULL, CONFLICTING);
+  rule(EXTENDABLE_ARRAY, STRING_OR_NULL, CONFLICTING);
+  rule(EXTENDABLE_ARRAY, NULL, CONFLICTING);
+  rule(EXTENDABLE_ARRAY, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(CONFLICTING, compiler));
-  Expect.equals(nonPrimitive2,
-                nonPrimitive2.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(nonPrimitive1, compiler));
-  Expect.equals(nonPrimitive2,
-                nonPrimitive2.intersection(nonPrimitive2, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(potentialArray, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(potentialString, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                nonPrimitive2.intersection(FIXED_ARRAY, compiler));
+  rule(nonPrimitive1, nonPrimitive1, nonPrimitive1);
+  rule(nonPrimitive1, nonPrimitive2, CONFLICTING);
+  rule(nonPrimitive1, potentialArray, CONFLICTING);
+  rule(nonPrimitive1, potentialString, CONFLICTING);
+  rule(nonPrimitive1, BOOLEAN_OR_NULL, CONFLICTING);
+  rule(nonPrimitive1, NUMBER_OR_NULL, CONFLICTING);
+  rule(nonPrimitive1, INTEGER_OR_NULL, CONFLICTING);
+  rule(nonPrimitive1, DOUBLE_OR_NULL, CONFLICTING);
+  rule(nonPrimitive1, STRING_OR_NULL, CONFLICTING);
+  rule(nonPrimitive1, NULL, CONFLICTING);
+  rule(nonPrimitive1, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                potentialArray.intersection(CONFLICTING, compiler));
-  Expect.equals(potentialArray,
-                potentialArray.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                potentialArray.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                potentialArray.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                potentialArray.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                potentialArray.intersection(DOUBLE, compiler));
-  Expect.equals(READABLE_ARRAY,
-                potentialArray.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                potentialArray.intersection(STRING, compiler));
-  Expect.equals(READABLE_ARRAY,
-                potentialArray.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(MUTABLE_ARRAY,
-                potentialArray.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(EXTENDABLE_ARRAY,
-                potentialArray.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                potentialArray.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                potentialArray.intersection(nonPrimitive2, compiler));
-  Expect.equals(potentialArray,
-                potentialArray.intersection(potentialArray, compiler));
-  Expect.equals(NULL,
-                potentialArray.intersection(potentialString, compiler));
-  Expect.equals(NULL,
-                potentialArray.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NULL,
-                potentialArray.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                potentialArray.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                potentialArray.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(NULL,
-                potentialArray.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(NULL,
-                potentialArray.intersection(NULL, compiler));
-  Expect.equals(FIXED_ARRAY,
-                potentialArray.intersection(FIXED_ARRAY, compiler));
+  rule(nonPrimitive2, nonPrimitive2, nonPrimitive2);
+  rule(nonPrimitive2, potentialArray, CONFLICTING);
+  rule(nonPrimitive2, potentialString, CONFLICTING);
+  rule(nonPrimitive2, BOOLEAN_OR_NULL, CONFLICTING);
+  rule(nonPrimitive2, NUMBER_OR_NULL, CONFLICTING);
+  rule(nonPrimitive2, INTEGER_OR_NULL, CONFLICTING);
+  rule(nonPrimitive2, DOUBLE_OR_NULL, CONFLICTING);
+  rule(nonPrimitive2, STRING_OR_NULL, CONFLICTING);
+  rule(nonPrimitive2, NULL, CONFLICTING);
+  rule(nonPrimitive2, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                potentialString.intersection(CONFLICTING, compiler));
-  Expect.equals(potentialString,
-                potentialString.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                potentialString.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                potentialString.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                potentialString.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                potentialString.intersection(DOUBLE, compiler));
-  Expect.equals(STRING,
-                potentialString.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(STRING,
-                potentialString.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                potentialString.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                potentialString.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                potentialString.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                potentialString.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                potentialString.intersection(nonPrimitive2, compiler));
-  Expect.equals(NULL,
-                potentialString.intersection(potentialArray, compiler));
-  Expect.equals(potentialString,
-                potentialString.intersection(potentialString, compiler));
-  Expect.equals(NULL,
-                potentialString.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NULL,
-                potentialString.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                potentialString.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                potentialString.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(STRING_OR_NULL,
-                potentialString.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(NULL,
-                potentialString.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                potentialString.intersection(FIXED_ARRAY, compiler));
+  rule(potentialArray, potentialArray, potentialArray);
+  rule(potentialArray, potentialString, NULL);
+  rule(potentialArray, BOOLEAN_OR_NULL, NULL);
+  rule(potentialArray, NUMBER_OR_NULL, NULL);
+  rule(potentialArray, INTEGER_OR_NULL, NULL);
+  rule(potentialArray, DOUBLE_OR_NULL, NULL);
+  rule(potentialArray, STRING_OR_NULL, NULL);
+  rule(potentialArray, NULL, NULL);
+  rule(potentialArray, FIXED_ARRAY, FIXED_ARRAY);
 
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(CONFLICTING, compiler));
-  Expect.equals(BOOLEAN_OR_NULL,
-                BOOLEAN_OR_NULL.intersection(UNKNOWN, compiler));
-  Expect.equals(BOOLEAN,
-                BOOLEAN_OR_NULL.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(nonPrimitive2, compiler));
-  Expect.equals(NULL,
-                BOOLEAN_OR_NULL.intersection(potentialArray, compiler));
-  Expect.equals(NULL,
-                BOOLEAN_OR_NULL.intersection(potentialString, compiler));
-  Expect.equals(BOOLEAN_OR_NULL,
-                BOOLEAN_OR_NULL.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NULL,
-                BOOLEAN_OR_NULL.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                BOOLEAN_OR_NULL.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                BOOLEAN_OR_NULL.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(NULL,
-                BOOLEAN_OR_NULL.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(NULL,
-                BOOLEAN_OR_NULL.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                BOOLEAN_OR_NULL.intersection(FIXED_ARRAY, compiler));
+  rule(potentialString, potentialString, potentialString);
+  rule(potentialString, BOOLEAN_OR_NULL, NULL);
+  rule(potentialString, NUMBER_OR_NULL, NULL);
+  rule(potentialString, INTEGER_OR_NULL, NULL);
+  rule(potentialString, DOUBLE_OR_NULL, NULL);
+  rule(potentialString, STRING_OR_NULL, STRING_OR_NULL);
+  rule(potentialString, NULL, NULL);
+  rule(potentialString, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                NUMBER_OR_NULL.intersection(CONFLICTING, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER_OR_NULL.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER_OR_NULL.intersection(BOOLEAN, compiler));
-  Expect.equals(NUMBER,
-                NUMBER_OR_NULL.intersection(NUMBER, compiler));
-  Expect.equals(INTEGER,
-                NUMBER_OR_NULL.intersection(INTEGER, compiler));
-  Expect.equals(DOUBLE,
-                NUMBER_OR_NULL.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER_OR_NULL.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER_OR_NULL.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER_OR_NULL.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER_OR_NULL.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER_OR_NULL.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER_OR_NULL.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER_OR_NULL.intersection(nonPrimitive2, compiler));
-  Expect.equals(NULL,
-                NUMBER_OR_NULL.intersection(potentialArray, compiler));
-  Expect.equals(NULL,
-                NUMBER_OR_NULL.intersection(potentialString, compiler));
-  Expect.equals(NULL,
-                NUMBER_OR_NULL.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NUMBER_OR_NULL,
-                NUMBER_OR_NULL.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                NUMBER_OR_NULL.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                NUMBER_OR_NULL.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(NULL,
-                NUMBER_OR_NULL.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(NULL,
-                NUMBER_OR_NULL.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                NUMBER_OR_NULL.intersection(FIXED_ARRAY, compiler));
+  rule(BOOLEAN_OR_NULL, BOOLEAN_OR_NULL, BOOLEAN_OR_NULL);
+  rule(BOOLEAN_OR_NULL, NUMBER_OR_NULL, NULL);
+  rule(BOOLEAN_OR_NULL, INTEGER_OR_NULL, NULL);
+  rule(BOOLEAN_OR_NULL, DOUBLE_OR_NULL, NULL);
+  rule(BOOLEAN_OR_NULL, STRING_OR_NULL, NULL);
+  rule(BOOLEAN_OR_NULL, NULL, NULL);
+  rule(BOOLEAN_OR_NULL, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                INTEGER_OR_NULL.intersection(CONFLICTING, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                INTEGER_OR_NULL.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER_OR_NULL.intersection(BOOLEAN, compiler));
-  Expect.equals(INTEGER,
-                INTEGER_OR_NULL.intersection(NUMBER, compiler));
-  Expect.equals(INTEGER,
-                INTEGER_OR_NULL.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER_OR_NULL.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER_OR_NULL.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER_OR_NULL.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER_OR_NULL.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER_OR_NULL.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER_OR_NULL.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER_OR_NULL.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER_OR_NULL.intersection(nonPrimitive2, compiler));
-  Expect.equals(NULL,
-                INTEGER_OR_NULL.intersection(potentialArray, compiler));
-  Expect.equals(NULL,
-                INTEGER_OR_NULL.intersection(potentialString, compiler));
-  Expect.equals(NULL,
-                INTEGER_OR_NULL.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                INTEGER_OR_NULL.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(INTEGER_OR_NULL,
-                INTEGER_OR_NULL.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                INTEGER_OR_NULL.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(NULL,
-                INTEGER_OR_NULL.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(NULL,
-                INTEGER_OR_NULL.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                INTEGER_OR_NULL.intersection(FIXED_ARRAY, compiler));
+  rule(NUMBER_OR_NULL, NUMBER_OR_NULL, NUMBER_OR_NULL);
+  rule(NUMBER_OR_NULL, INTEGER_OR_NULL, INTEGER_OR_NULL);
+  rule(NUMBER_OR_NULL, DOUBLE_OR_NULL, DOUBLE_OR_NULL);
+  rule(NUMBER_OR_NULL, STRING_OR_NULL, NULL);
+  rule(NUMBER_OR_NULL, NULL, NULL);
+  rule(NUMBER_OR_NULL, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                DOUBLE_OR_NULL.intersection(CONFLICTING, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                DOUBLE_OR_NULL.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE_OR_NULL.intersection(BOOLEAN, compiler));
-  Expect.equals(DOUBLE,
-                DOUBLE_OR_NULL.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE_OR_NULL.intersection(INTEGER, compiler));
-  Expect.equals(DOUBLE,
-                DOUBLE_OR_NULL.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE_OR_NULL.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE_OR_NULL.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE_OR_NULL.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE_OR_NULL.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE_OR_NULL.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE_OR_NULL.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE_OR_NULL.intersection(nonPrimitive2, compiler));
-  Expect.equals(NULL,
-                DOUBLE_OR_NULL.intersection(potentialArray, compiler));
-  Expect.equals(NULL,
-                DOUBLE_OR_NULL.intersection(potentialString, compiler));
-  Expect.equals(NULL,
-                DOUBLE_OR_NULL.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                DOUBLE_OR_NULL.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                DOUBLE_OR_NULL.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(DOUBLE_OR_NULL,
-                DOUBLE_OR_NULL.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(NULL,
-                DOUBLE_OR_NULL.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(NULL,
-                DOUBLE_OR_NULL.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                DOUBLE_OR_NULL.intersection(FIXED_ARRAY, compiler));
+  rule(INTEGER_OR_NULL, INTEGER_OR_NULL, INTEGER_OR_NULL);
+  rule(INTEGER_OR_NULL, DOUBLE_OR_NULL, NULL);
+  rule(INTEGER_OR_NULL, STRING_OR_NULL, NULL);
+  rule(INTEGER_OR_NULL, NULL, NULL);
+  rule(INTEGER_OR_NULL, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                STRING_OR_NULL.intersection(CONFLICTING, compiler));
-  Expect.equals(STRING_OR_NULL,
-                STRING_OR_NULL.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                STRING_OR_NULL.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                STRING_OR_NULL.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                STRING_OR_NULL.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                STRING_OR_NULL.intersection(DOUBLE, compiler));
-  Expect.equals(STRING,
-                STRING_OR_NULL.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(STRING,
-                STRING_OR_NULL.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                STRING_OR_NULL.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                STRING_OR_NULL.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                STRING_OR_NULL.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                STRING_OR_NULL.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                STRING_OR_NULL.intersection(nonPrimitive2, compiler));
-  Expect.equals(NULL,
-                STRING_OR_NULL.intersection(potentialArray, compiler));
-  Expect.equals(STRING_OR_NULL,
-                STRING_OR_NULL.intersection(potentialString, compiler));
-  Expect.equals(NULL,
-                STRING_OR_NULL.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NULL,
-                STRING_OR_NULL.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                STRING_OR_NULL.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                STRING_OR_NULL.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(STRING_OR_NULL,
-                STRING_OR_NULL.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(NULL,
-                STRING_OR_NULL.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                STRING_OR_NULL.intersection(FIXED_ARRAY, compiler));
+  rule(DOUBLE_OR_NULL, DOUBLE_OR_NULL, DOUBLE_OR_NULL);
+  rule(DOUBLE_OR_NULL, STRING_OR_NULL, NULL);
+  rule(DOUBLE_OR_NULL, NULL, NULL);
+  rule(DOUBLE_OR_NULL, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                NULL.intersection(CONFLICTING, compiler));
-  Expect.equals(NULL,
-                NULL.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(DOUBLE, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(STRING, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(nonPrimitive2, compiler));
-  Expect.equals(NULL,
-                NULL.intersection(potentialArray, compiler));
-  Expect.equals(NULL,
-                NULL.intersection(potentialString, compiler));
-  Expect.equals(NULL,
-                NULL.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(NULL,
-                NULL.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                NULL.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(NULL,
-                NULL.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(NULL,
-                NULL.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(NULL,
-                NULL.intersection(NULL, compiler));
-  Expect.equals(CONFLICTING,
-                NULL.intersection(FIXED_ARRAY, compiler));
+  rule(STRING_OR_NULL, STRING_OR_NULL, STRING_OR_NULL);
+  rule(STRING_OR_NULL, NULL, NULL);
+  rule(STRING_OR_NULL, FIXED_ARRAY, CONFLICTING);
 
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(CONFLICTING, compiler));
-  Expect.equals(FIXED_ARRAY,
-                FIXED_ARRAY.intersection(UNKNOWN, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(BOOLEAN, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(NUMBER, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(INTEGER, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(DOUBLE, compiler));
-  Expect.equals(FIXED_ARRAY,
-                FIXED_ARRAY.intersection(INDEXABLE_PRIMITIVE, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(STRING, compiler));
-  Expect.equals(FIXED_ARRAY,
-                FIXED_ARRAY.intersection(READABLE_ARRAY, compiler));
-  Expect.equals(FIXED_ARRAY,
-                FIXED_ARRAY.intersection(MUTABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(EXTENDABLE_ARRAY, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(nonPrimitive1, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(nonPrimitive2, compiler));
-  Expect.equals(FIXED_ARRAY,
-                FIXED_ARRAY.intersection(potentialArray, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(potentialString, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(BOOLEAN_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(NUMBER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(INTEGER_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(DOUBLE_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(STRING_OR_NULL, compiler));
-  Expect.equals(CONFLICTING,
-                FIXED_ARRAY.intersection(NULL, compiler));
-  Expect.equals(FIXED_ARRAY,
-                FIXED_ARRAY.intersection(FIXED_ARRAY, compiler));
+  rule(NULL, NULL, NULL);
+  rule(NULL, FIXED_ARRAY, CONFLICTING);
+
+  rule(FIXED_ARRAY, FIXED_ARRAY, FIXED_ARRAY);
+
+  ruleSet.validateCoverage();
 }
 
 void testRegressions(MockCompiler compiler) {
@@ -2062,6 +694,8 @@
       compiler.listClass.computeType(compiler), compiler);
   potentialString = new HType.subtype(
       patternClass.computeType(compiler), compiler);
+  jsInterceptor = new HType.nonNullSubclass(
+      compiler.backend.jsInterceptorClass.computeType(compiler), compiler);
   jsArrayOrNull = new HType.subclass(
       compiler.backend.jsArrayClass.computeType(compiler), compiler);
   jsMutableArrayOrNull = new HType.subclass(
@@ -2072,6 +706,8 @@
       compiler.backend.jsExtendableArrayClass.computeType(compiler), compiler);
   jsIndexableOrNull = new HType.subtype(
       compiler.backend.jsIndexableClass.computeType(compiler), compiler);
+  jsInterceptorOrNull = new HType.subclass(
+      compiler.backend.jsInterceptorClass.computeType(compiler), compiler);
 
   testUnion(compiler);
   testIntersection(compiler);
diff --git a/tests/html/dom_isolates_test.dart b/tests/html/dom_isolates_test.dart
index b630f75..7ce1386 100644
--- a/tests/html/dom_isolates_test.dart
+++ b/tests/html/dom_isolates_test.dart
@@ -8,7 +8,7 @@
 import 'dart:html';
 import 'dart:isolate';
 
-isolateMain() {
+childDomIsolate() {
   port.receive((msg, replyTo) {
     if (msg != 'check') {
       replyTo.send('wrong msg: $msg');
@@ -18,33 +18,38 @@
   });
 }
 
-isolateMainTrampoline() {
-  final childPort = spawnDomFunction(isolateMain);
+trampolineIsolate() {
+  final future = spawnDomFunction(childDomIsolate);
   port.receive((msg, parentPort) {
-    childPort.call(msg).then((response) {
-      parentPort.send(response);
-      port.close();
+    future.then((childPort) {
+      childPort.call(msg).then((response) {
+        parentPort.send(response);
+        port.close();
+      });
     });
   });
 }
 
-dummy() => print("Bad invocation of top-level function");
+dummy() => print('Bad invocation of top-level function');
 
 main() {
   useHtmlConfiguration();
 
   test('Simple DOM isolate test', () {
-    spawnDomFunction(isolateMain).call('check').then(
-      expectAsync1((msg) {
-        expect(msg, equals('${window.location}'));
-      }));
+    spawnDomFunction(childDomIsolate).then((sendPort) {
+      expect(sendPort.call('check'), completion('${window.location}'));
+    });
   });
 
   test('Nested DOM isolates test', () {
-    spawnDomFunction(isolateMainTrampoline).call('check').then(
-      expectAsync1((msg) {
-        expect(msg, equals('${window.location}'));
-      }));
+    spawnDomFunction(trampolineIsolate).then((sendPort) {
+      expect(sendPort.call('check'), completion('${window.location}'));
+    });
+  });
+
+  test('Spawn DOM isolate from pure', () {
+    expect(spawnFunction(trampolineIsolate).call('check'),
+           completion('${window.location}'));
   });
 
   test('Not function', () {
@@ -58,7 +63,7 @@
 
   test('Masked local function', () {
     var local = 42;
-    dummy() => print("Bad invocation of local function: $local");
+    dummy() => print('Bad invocation of local function: $local');
     expect(() => spawnDomFunction(dummy), throws);
   });
 }
diff --git a/tests/html/html.status b/tests/html/html.status
index b7ecd42..0d45af0 100644
--- a/tests/html/html.status
+++ b/tests/html/html.status
@@ -9,6 +9,16 @@
 custom_elements_test: Skip # Not yet implemented.
 interactive_test: Skip # Must be run manually.
 
+[ $compiler == dart2js]
+dom_isolates_test: Skip # Need to migrate to new spawnDomFunction.
+
+[ $compiler == dart2js && $runtime == ie10 ]
+indexeddb_3_test: Pass, Timeout, Slow # Issue: http://dartbug.com/9437
+indexeddb_4_test: Pass, Timeout, Slow # Issue: http://dartbug.com/9437
+
+[ $compiler == dart2js && $csp && $runtime == drt && $unchecked ]
+indexeddb_2_test: Fail, Crash, Pass # Bug in v8, http://dartbug.com/9407
+
 # Layout tests are only supported on DRT.
 [ $runtime == ie9 || $runtime == ie10 || $runtime == safari || $runtime == ff || $runtime == chrome || $runtime == opera ]
 *layout_test: Skip
@@ -19,9 +29,8 @@
 [$runtime == drt || $runtime == dartium || $runtime == chrome]
 webgl_1_test: Pass, Fail # Issue 8219
 
-[ $runtime == drt || ($runtime == chrome && $system == windows) ]
-audiobuffersourcenode_test: Pass, Fail, Timeout, Crash # AudiobufferSourceNode is flaky on Chrome and Dartium - filed issue 8021 for the timeout.
-audiocontext_test: Pass, Timeout, Crash  # Issue 8021.
+[ $runtime == drt ]
+audiocontext_test: Skip # Issue 9322
 
 [ $compiler == none && ($runtime == drt || $runtime == dartium) ]
 request_animation_frame_test: Skip   # drt hangs; requestAnimationFrame not implemented
diff --git a/tests/html/interactive_test.dart b/tests/html/interactive_test.dart
index 47bbe08..02d1dda 100644
--- a/tests/html/interactive_test.dart
+++ b/tests/html/interactive_test.dart
@@ -93,4 +93,46 @@
       });
     }
   });
+
+  group('KeyEvent', () {
+    keydownHandlerTest(KeyEvent e) {
+      document.body.innerHtml =
+          '${document.body.innerHtml}KeyDOWN: CharCode: ${e.charCode}, KeyCode:'
+          ' ${e.keyCode}<br />';
+      expect(e.charCode, 0);
+    }
+    keypressHandlerTest(KeyEvent e) {
+      document.body.innerHtml =
+          '${document.body.innerHtml}KeyPRESS: CharCode: ${e.charCode}, '
+          'KeyCode: ${e.keyCode}<br />';
+    }
+    keyupHandlerTest(KeyEvent e) {
+      document.body.innerHtml =
+          '${document.body.innerHtml}KeyUP: CharCode: ${e.charCode}, KeyCode:'
+          ' ${e.keyCode}<br />';
+      expect(e.charCode, 0);
+    }
+    keyupHandlerTest2(KeyEvent e) {
+      document.body.innerHtml =
+          '${document.body.innerHtml}A second KeyUP handler: CharCode: '
+          '${e.charCode}, KeyCode: ${e.keyCode}<br />';
+      expect(e.charCode, 0);
+    }
+    test('keys', () {
+      document.body.innerHtml =
+          '${document.body.innerHtml}To test keyboard event values, press some '
+          'keys on your keyboard.<br /><br />The charcode for keydown and keyup'
+          ' should be 0, and the keycode should (generally) be populated with a'
+          ' value. Keycode and charcode should both have values for the '
+          'keypress event.';
+      KeyboardEventStream.onKeyDown(document.body).listen(
+          keydownHandlerTest);
+      KeyboardEventStream.onKeyPress(document.body).listen(
+          keypressHandlerTest);
+      KeyboardEventStream.onKeyUp(document.body).listen(
+          keyupHandlerTest);
+      KeyboardEventStream.onKeyUp(document.body).listen(
+          keyupHandlerTest2);
+    });
+  });
 }
diff --git a/tests/html/keyboard_event_test.dart b/tests/html/keyboard_event_test.dart
index da0842a..f742735 100644
--- a/tests/html/keyboard_event_test.dart
+++ b/tests/html/keyboard_event_test.dart
@@ -23,9 +23,9 @@
     // values (a KeyboardEvent can be "init"-ed but not all the information can
     // be programmatically populated. It exists as an example for how to use
     // KeyboardEventController more than anything else.
-    var controller = new KeyboardEventController.keydown(document.body);
-    var func = keydownHandlerTest;
-    controller.add(func);
+    KeyboardEventStream.onKeyDown(document.body).listen(
+        keydownHandlerTest);
+    KeyEvent.keyDownEvent.forTarget(document.body).listen(keydownHandlerTest);
     document.body.onKeyDown.listen((e) => print('regular listener'));
   });
 }
diff --git a/tests/isolate/isolate.status b/tests/isolate/isolate.status
index de88329..9f7e85a 100644
--- a/tests/isolate/isolate.status
+++ b/tests/isolate/isolate.status
@@ -2,6 +2,15 @@
 # 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.
 
+[ $compiler == dart2js && $csp && $runtime == drt && $unchecked ]
+mandel_isolate_stream_test: Fail, Crash # Bug in v8, http://dartbug.com/9407
+nested_spawn_stream2_test: Fail, Crash # Bug in v8, http://dartbug.com/9407
+count_test: Fail, Crash # Bug in v8, http://dartbug.com/9407
+count_stream_test: Fail, Crash # Bug in v8, http://dartbug.com/9407
+mandel_isolate_test: Fail, Crash # Bug in v8, http://dartbug.com/9407
+mint_maker_test: Fail, Crash # Bug in v8, http://dartbug.com/9407
+
+
 [ $runtime == vm ]
 isolate2_negative_test: Skip  # Need to resolve correct behaviour.
 isolate3_negative_test: Skip  # test depends on isolate error exiting process.
@@ -54,6 +63,7 @@
 global_error_handler_stream_test: Pass, Fail # http://dartbug.com/9012 and http://dartbug.com/9024
 global_error_handler2_test: Pass, Fail # http://dartbug.com/9012 and http://dartbug.com/9024
 global_error_handler_stream2_test: Pass, Fail # http://dartbug.com/9012 and http://dartbug.com/9024
+typed_data_message_test: Fail # dart:typeddata not supported in dart2js yet.
 
 [ $runtime == safari ]
 cross_isolate_message_test: Skip      # Depends on 32/64 bit Safari. See Issue 1120
@@ -104,6 +114,7 @@
 
 [ $compiler == dart2js && $runtime == ff && ($system == windows || $system == linux) ]
 mandel_isolate_test: Pass, Fail, Timeout # Issue 7952
+mandel_isolate_stream_test: Pass, Fail, Timeout # Issue 7952
 
 [ $arch == arm ]
 *: Skip
diff --git a/tests/isolate/isolate_import_negative_test.dart b/tests/isolate/isolate_import_negative_test.dart
index 38199ea..0f5a042 100644
--- a/tests/isolate/isolate_import_negative_test.dart
+++ b/tests/isolate/isolate_import_negative_test.dart
@@ -3,8 +3,8 @@
 // BSD-style license that can be found in the LICENSE file.
 
 library IsolateImportNegativeTest;
-// Ommiting the following import is an error:
-// #import('dart:isolate');
+// Omitting the following import is an error:
+// import 'dart:isolate';
 
 void entry() {}
 
diff --git a/tests/isolate/typed_data_message_test.dart b/tests/isolate/typed_data_message_test.dart
new file mode 100644
index 0000000..3631ded
--- /dev/null
+++ b/tests/isolate/typed_data_message_test.dart
@@ -0,0 +1,97 @@
+// Copyright (c) 2012, 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.
+
+// Dart test program for testing serialization of messages.
+// VMOptions=--enable_type_checks --enable_asserts
+
+library TypedDataMessageTest;
+import 'dart:isolate';
+import 'dart:typeddata';
+import '../../pkg/unittest/lib/unittest.dart';
+
+// ---------------------------------------------------------------------------
+// Message passing test.
+// ---------------------------------------------------------------------------
+
+List elements;
+
+void initializeList() {
+  elements = new List(3);
+  elements[0] = new Int8List(10);
+  for (int j = 0; j < 10; j++) {
+    elements[0][j] = j;
+  }
+  elements[1] = new ByteData.view(elements[0].buffer, 0, 10);
+  for (int j = 0; j < 10; j++) {
+    elements[1].setInt8(j, j + 100);
+  }
+  elements[2] = new Int8List.view(new Int8List(100).buffer, 50, 10);
+  for (int j = 0; j < 10; j++) {
+    elements[2][j] = j + 250;
+  }
+}
+
+void VerifyList(List expected, List actual) {
+  for (int i = 0; i < expected.length; i++) {
+    expect(actual[i], expected[i]);
+  }
+}
+
+void VerifyBytedata(ByteData expected, ByteData actual) {
+  for (int i = 0; i < expected.length; i++) {
+    expect(actual.getInt8(i), expected.getInt8(i));
+  }
+}
+
+void VerifyObject(int index, var actual) {
+  var expected = elements[index];
+  if (expected is List) {
+    expect(actual, isList);
+    VerifyList(expected, actual);
+  } else {
+    expect(true, actual is ByteData);
+    VerifyBytedata(expected, actual);
+  }
+  expect(actual.length, expected.length);
+}
+
+pingPong() {
+  initializeList();
+  int count = 0;
+  port.receive((var message, SendPort replyTo) {
+    if (message == -1) {
+      port.close();
+      replyTo.send(count, null);
+    } else {
+      // Check if the received object is correct.
+      if (count < elements.length) {
+        VerifyObject(count, message);
+      }
+      // Bounce the received object back so that the sender
+      // can make sure that the object matches.
+      replyTo.send(message, null);
+      count++;
+    }
+  });
+}
+
+main() {
+  initializeList();
+  test("send objects and receive them back", () {
+    SendPort remote = spawnFunction(pingPong);
+    // Send objects and receive them back.
+    for (int i = 0; i < elements.length; i++) {
+      var sentObject = elements[i];
+      var idx = i;
+      remote.call(sentObject).then(expectAsync1((var receivedObject) {
+        VerifyObject(idx, receivedObject);
+      }));
+    }
+
+    // Shutdown the MessageServer.
+    remote.call(-1).then(expectAsync1((int message) {
+        expect(message, elements.length);
+      }));
+  });
+}
diff --git a/tests/language/constructor_initializer_test.dart b/tests/language/constructor_initializer_test.dart
new file mode 100644
index 0000000..a752ecd
--- /dev/null
+++ b/tests/language/constructor_initializer_test.dart
@@ -0,0 +1,37 @@
+// Copyright (c) 2013, 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.
+
+class A {
+  var _x, _y;
+  A(x, [y = 10]): _x = x++, _y = y++ {
+    // Check that value of modified constructor parameters
+    // is remembered in the constructor body.
+    Expect.equals(x, _x + 1);
+    Expect.equals(y, _y + 1);
+    Expect.isFalse(?y);
+  }
+}
+
+class B extends A {
+  var _a, _b;
+  // The super call in the middle of the initializer list conceptually
+  // forces two super call chains, one for initializer list and a second
+  // one for the constructor bodies.
+  B(a, b): _a = a++, super(a + b++), _b = b++ {
+    Expect.equals(a, _a + 1);
+    Expect.equals(b, _b + 1);
+    Expect.equals(a + (b-2), _x);
+  }
+}
+
+main() {
+  var o = new B(3, 5);
+  Expect.equals(3, o._a);
+  Expect.equals(6, o._b);
+  Expect.equals(9, o._x);
+  Expect.equals(10, o._y);
+  o = new A(3);
+  Expect.equals(3, o._x);
+  Expect.equals(10, o._y);
+}
diff --git a/tests/language/function_type_alias8_test.dart b/tests/language/function_type_alias8_test.dart
new file mode 100644
index 0000000..3d027c3
--- /dev/null
+++ b/tests/language/function_type_alias8_test.dart
@@ -0,0 +1,20 @@
+// Copyright (c) 2013, 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.
+
+// Regression test for issue 9442.
+
+typedef dynamic GetFromThing<T extends Thing>(T target);
+
+typedef GetFromThing<T> DefGetFromThing<T extends Thing>(dynamic def);
+
+class Thing { }
+
+class Test {
+  static final DefGetFromThing<Thing> fromThing = (dynamic def) { };
+}
+
+main() {
+  Test.fromThing(10);
+}
+
diff --git a/tests/language/function_type_alias_test.dart b/tests/language/function_type_alias_test.dart
index f6188b6..e1bf33b 100644
--- a/tests/language/function_type_alias_test.dart
+++ b/tests/language/function_type_alias_test.dart
@@ -87,11 +87,11 @@
     Expect.equals(99, test(minus, 100, 1));
 
     int plus (int a, [int b = 1]) { return a + b; };
-    Expect.isTrue(plus is !Fun);
-    Expect.isTrue(plus is !IntFun);
+    Expect.isTrue(plus is Fun);
+    Expect.isTrue(plus is IntFun);
     Expect.isTrue(plus is !BoolFun);
-    Expect.isTrue(plus is !CompareObj);
-    Expect.isTrue(plus is !CompareInt);
+    Expect.isTrue(plus is CompareObj);
+    Expect.isTrue(plus is CompareInt);
     Expect.isTrue(plus is !CompareString);
 
     Expect.equals(0, bar());
diff --git a/tests/language/getter_setter_order_test.dart b/tests/language/getter_setter_order_test.dart
new file mode 100644
index 0000000..0805df8
--- /dev/null
+++ b/tests/language/getter_setter_order_test.dart
@@ -0,0 +1,92 @@
+// Copyright (c) 2013, 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.
+
+// Test for the evaluation order of getters and setters.
+
+var trace;
+
+class X {
+  get b {
+    trace.add('get b');
+    return new X();
+  }
+
+  set c (value) {
+    trace.add('set c');
+  }
+
+  toString() {
+    trace.add('toString');
+    return 'X';
+  }
+
+  get c {
+    trace.add('get c');
+    return 42;
+  }
+
+  get d {
+    trace.add('get d');
+    return new X();
+  }
+
+  operator [] (index) {
+    trace.add('index');
+    return 42;
+  }
+
+  operator []=(index, value) {
+    trace.add('indexSet');
+  }
+}
+
+main() {
+  var x = new X();
+
+  trace = [];
+  x.b.c = '$x';
+  Expect.listEquals(['get b', 'toString', 'set c'], trace);
+
+  trace = [];
+  x.b.c += '$x'.hashCode;
+  Expect.listEquals(['get b', 'get c', 'toString', 'set c'], trace);
+
+  trace = [];
+  x.b.c++;
+  Expect.listEquals(['get b', 'get c', 'set c'], trace);
+
+  trace = [];
+  x.b.d[42] = '$x';
+  Expect.listEquals(['get b', 'get d', 'toString', 'indexSet'], trace);
+
+  trace = [];
+  x.b.d[42] += '$x'.hashCode;
+  Expect.listEquals(['get b', 'get d', 'index', 'toString', 'indexSet'], trace);
+
+  trace = [];
+  x.b.d[42]++;
+  Expect.listEquals(['get b', 'get d', 'index', 'indexSet'], trace);
+
+  trace = [];
+  ++x.b.d[42];
+  Expect.listEquals(['get b', 'get d', 'index', 'indexSet'], trace);
+
+  trace = [];
+  x.b.d[x.c] *= '$x'.hashCode;
+  Expect.listEquals(
+      ['get b', 'get d', 'get c', 'index', 'toString', 'indexSet'], trace);
+
+  trace = [];
+  x.b.c = x.d.c = '$x';
+  Expect.listEquals(['get b', 'get d', 'toString', 'set c', 'set c',], trace);
+
+  trace = [];
+  x.b.c = x.d[42] *= '$x'.hashCode;
+  Expect.listEquals(
+      ['get b', 'get d', 'index', 'toString', 'indexSet', 'set c'], trace);
+
+  trace = [];
+  x.b.c = ++x.d.c;
+  Expect.listEquals(['get b', 'get d', 'get c', 'set c', 'set c'], trace);
+}
diff --git a/tests/language/identical_test.dart b/tests/language/identical_test.dart
new file mode 100644
index 0000000..1533890
--- /dev/null
+++ b/tests/language/identical_test.dart
@@ -0,0 +1,36 @@
+// Copyright (c) 2013, 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.
+// Test efficient and correct implementation of !identical(a, b).
+
+notIdenticalTest1(a) {
+  if (!identical("ho", a)) {
+    return 2;
+  } else {
+    return 1;
+  }
+}
+
+notIdenticalTest2(a) {
+  var x = identical("ho", a);
+  if (!x) {
+    Expect.equals(false, x);
+    return x;
+  } else {
+    Expect.equals(true, x);
+    return 1;
+  }
+}
+
+notIdenticalTest3(a) {
+  var x = identical("ho", a);
+  return !x;
+}
+
+main() {
+  for (int i = 0; i < 10000; i++) {
+    Expect.equals(1, notIdenticalTest1("ho"));
+    Expect.equals(1, notIdenticalTest2("ho"));
+    Expect.equals(false, notIdenticalTest3("ho"));
+  }
+}
diff --git a/tests/language/interceptor8_test.dart b/tests/language/interceptor8_test.dart
new file mode 100644
index 0000000..0890124
--- /dev/null
+++ b/tests/language/interceptor8_test.dart
@@ -0,0 +1,12 @@
+// Copyright (c) 2013, 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.
+
+// Regression test for dart2js whose codegen used to not consider a double
+// could be instantiated when doing int / int.
+
+var a = [5, 2];
+
+main() {
+  print(a[0] / a[1]);
+}
diff --git a/tests/language/language.status b/tests/language/language.status
index b323119..c0234d1 100644
--- a/tests/language/language.status
+++ b/tests/language/language.status
@@ -27,6 +27,8 @@
 # These bugs refer currently ongoing language discussions.
 constructor5_test: Fail           # (Discussion ongoing)
 
+constructor_initializer_test: Fail # Side effects in constructor parameters
+
 constructor6_test: Fail           # Issue 6422
 closure_in_initializer_test: Fail # Issue 6422
 
@@ -336,6 +338,7 @@
 const_factory_redirection_test: Fail # http://dartbug.com/6894
 compile_time_constant_h_test: Fail
 constructor_redirect2_test/03: Fail
+constructor_initializer_test: Fail # VM issue
 factory_implementation_test/none: Fail
 factory_implementation_test/00:Fail
 factory2_test: Fail
diff --git a/tests/language/language_dart2js.status b/tests/language/language_dart2js.status
index f288df9..9f28309 100644
--- a/tests/language/language_dart2js.status
+++ b/tests/language/language_dart2js.status
@@ -141,13 +141,13 @@
 canonical_const_test: Fail # We don't take the generic type into account yet.
 
 # Support for optional parameters not conform to latest spec.
-function_type_alias_test: Fail
+typedef_is_test: Fail # http://dartbug.com/9058
+function_type_alias_test: Fail # http://dartbug.com/9058
 function_type_alias2_test: Fail
 named_parameters_type_test: Fail
 positional_parameters_type_test: Fail
 named_parameters_with_object_property_names_test: Fail
 
-
 # Compilation errors.
 default_factory3_test: Fail # type arguments on redirecting factory not implemented
 non_parameterized_factory_test: Fail # type arguments on redirecting factory not implemented
diff --git a/tests/language/library1_lib.lib b/tests/language/library1_lib.lib
index 33a8fb9..c675668 100644
--- a/tests/language/library1_lib.lib
+++ b/tests/language/library1_lib.lib
@@ -2,6 +2,6 @@
 // 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("Library1Lib");
+library Library1Lib;
 
-#source("library1_lib.dart");
+part "library1_lib.dart";
diff --git a/tests/language/library_prefixes.lib b/tests/language/library_prefixes.lib
index c534b5c..27165b7 100644
--- a/tests/language/library_prefixes.lib
+++ b/tests/language/library_prefixes.lib
@@ -2,8 +2,8 @@
 // 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("LibraryPrefixes.lib");
+library LibraryPrefixes.lib;
 
-#import("library_prefixes_test1.lib");
-#import("library_prefixes_test2.lib", prefix:"other");
-#source("library_prefixes.dart");
+import "library_prefixes_test1.lib";
+import "library_prefixes_test2.lib" as other;
+part "library_prefixes.dart";
diff --git a/tests/language/library_prefixes_test1.lib b/tests/language/library_prefixes_test1.lib
index 51cccaa..8767100 100644
--- a/tests/language/library_prefixes_test1.lib
+++ b/tests/language/library_prefixes_test1.lib
@@ -2,6 +2,6 @@
 // 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("LibraryPrefixesTest1.lib");
+library LibraryPrefixesTest1.lib;
 
-#source("library_prefixes_test1.dart");
+part "library_prefixes_test1.dart";
diff --git a/tests/language/library_prefixes_test2.lib b/tests/language/library_prefixes_test2.lib
index b576075..b6e77cf 100644
--- a/tests/language/library_prefixes_test2.lib
+++ b/tests/language/library_prefixes_test2.lib
@@ -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.
 
-#library("LibraryPrefixesTest2.lib");
+library LibraryPrefixesTest2.lib;
 
-#source("library_prefixes_test2.dart");
+part "library_prefixes_test2.dart";
 
diff --git a/tests/language/private2_lib.lib b/tests/language/private2_lib.lib
index b381684..6290ecb 100644
--- a/tests/language/private2_lib.lib
+++ b/tests/language/private2_lib.lib
@@ -3,7 +3,7 @@
 // BSD-style license that can be found in the LICENSE file.
 // Dart test for testing access to private fields across class hierarchies.
 
-#library("Private2Lib");
+library Private2Lib;
 
-#import("private2_test.dart");
-#source("private2_lib.dart");
+import "private2_test.dart";
+part "private2_lib.dart";
diff --git a/tests/language/private_lib b/tests/language/private_lib
index a8ee809..d4ce18b 100644
--- a/tests/language/private_lib
+++ b/tests/language/private_lib
@@ -3,6 +3,6 @@
 // BSD-style license that can be found in the LICENSE file.
 // Dart test for testing access to private fields.
 
-#library("PrivateLib");
+library PrivateLib;
 
-#source("private_lib.dart");
+part "private_lib.dart";
diff --git a/tests/language/private_other.lib b/tests/language/private_other.lib
index 2f2f42f..b03c39d 100644
--- a/tests/language/private_other.lib
+++ b/tests/language/private_other.lib
@@ -4,7 +4,7 @@
 
 // Dart test for testing access to private fields.
 
-#library("PrivateOther");
+library PrivateOther;
 
-#import("private_test.dart");
-#source("private3.dart");
+import "private_test.dart";
+part "private3.dart";
diff --git a/tests/language/top_level_prefixed_library_test.lib b/tests/language/top_level_prefixed_library_test.lib
index 617e625..d75930d 100644
--- a/tests/language/top_level_prefixed_library_test.lib
+++ b/tests/language/top_level_prefixed_library_test.lib
@@ -2,5 +2,5 @@
 // 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('TopLevelPrefixedLibrary');
-#source('top_level_file2.dart');
+library TopLevelPrefixedLibrary;
+part 'top_level_file2.dart';
diff --git a/tests/language/typedef_is_test.dart b/tests/language/typedef_is_test.dart
index 56c6d37..768eb4c 100644
--- a/tests/language/typedef_is_test.dart
+++ b/tests/language/typedef_is_test.dart
@@ -59,9 +59,9 @@
   Expect.isFalse(func5 is Func7);
 
   int func6([int i, int j, int k]) {}
-  Expect.isFalse(func6 is Func1);
-  Expect.isFalse(func6 is Func2);
-  Expect.isFalse(func6 is Func3);
+  Expect.isTrue(func6 is Func1);
+  Expect.isTrue(func6 is Func2);
+  Expect.isTrue(func6 is Func3);
   Expect.isTrue(func6 is Func4);
   Expect.isFalse(func6 is Func5);
   Expect.isFalse(func6 is Func6);
diff --git a/tests/lib/lib.status b/tests/lib/lib.status
index 4e76f32..84436a5 100644
--- a/tests/lib/lib.status
+++ b/tests/lib/lib.status
@@ -4,9 +4,15 @@
 
 async/stream_periodic4_test: Pass, Fail # Issue http://dartbug.com/9367
 
-# The scalarlist library is not supported by dart2js or dart2dart yet.
+# The typeddata library is not supported by dart2js or dart2dart yet.
 [ $compiler == dart2js  || $compiler == dart2dart ]
-scalarlist/*: Skip
+typeddata/*: Fail
+
+
+# The typeddata library is not supported by dart2js or dart2dart yet.
+[ $compiler == dart2js  || $compiler == dart2dart ]
+typeddata/*: Skip
+
 
 [ $compiler == dart2js ]
 math/*: Skip
@@ -14,6 +20,9 @@
 async/run_async3_test: Fail # _enqueueImmediate runs after Timer. http://dartbug.com/9002
 async/run_async4_test: Pass, Fail # no global exception handler in isolates. http://dartbug.com/9012
 
+[ $compiler == dart2js && $runtime == chrome && $system == macos]
+crypto/hmac_sha1_test: Fail # Issue 9471
+
 [ $compiler == dart2js && $checked ]
 async/stream_event_transform_test: Fail # Issue 7733.
 
diff --git a/tests/lib/scalarlist/float32x4_list_test.dart b/tests/lib/typeddata/float32x4_list_test.dart
similarity index 95%
rename from tests/lib/scalarlist/float32x4_list_test.dart
rename to tests/lib/typeddata/float32x4_list_test.dart
index 2073aff..3fffde0 100644
--- a/tests/lib/scalarlist/float32x4_list_test.dart
+++ b/tests/lib/typeddata/float32x4_list_test.dart
@@ -5,7 +5,7 @@
 // Library tag to be able to run in html test framework.
 library float32x4_list_test;
 
-import 'dart:scalarlist';
+import 'dart:typeddata';
 
 testLoadStore(array) {
   Expect.equals(8, array.length);
@@ -56,7 +56,7 @@
   for (int i = 0; i < floatList.length; i++) {
     floatList[i] = i.toDouble();
   }
-  list = new Float32x4List.view(floatList.asByteArray());
+  list = new Float32x4List.view(floatList);
   for (int i = 0; i < 3000; i++) {
     testView(list);
   }
diff --git a/tests/lib/scalarlist/float32x4_test.dart b/tests/lib/typeddata/float32x4_test.dart
similarity index 99%
rename from tests/lib/scalarlist/float32x4_test.dart
rename to tests/lib/typeddata/float32x4_test.dart
index 943f28b..deb0ce8 100644
--- a/tests/lib/scalarlist/float32x4_test.dart
+++ b/tests/lib/typeddata/float32x4_test.dart
@@ -5,7 +5,7 @@
 // Library tag to be able to run in html test framework.
 library float32x4_test;
 
-import 'dart:scalarlist';
+import 'dart:typeddata';
 
 testAdd() {
   var m = new Float32x4(-1.0, -2.0, -3.0, -4.0);
@@ -351,13 +351,13 @@
 
 main() {
   for (int i = 0; i < 3000; i++) {
+    testAdd();
     testGetters();
     testSetters();
     testBitOperators();
     testConversions();
     testSelect();
     testShuffle();
-    testAdd();
     testSub();
     testNegate();
     testMul();
diff --git a/tests/standalone/byte_array_test.dart b/tests/standalone/byte_array_test.dart
deleted file mode 100644
index dd5e232..0000000
--- a/tests/standalone/byte_array_test.dart
+++ /dev/null
@@ -1,289 +0,0 @@
-// Copyright (c) 2012, 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.
-//
-// Dart test program for testing native byte arrays.
-
-// Library tag to be able to run in html test framework.
-library ByteArrayTest;
-
-import 'dart:scalarlist';
-
-void testCreateUint8ByteArray() {
-  Uint8List byteArray;
-
-  byteArray = new Uint8List(0);
-  Expect.isTrue(byteArray is Uint8List);
-  Expect.isFalse(byteArray is Uint8ClampedList);
-  Expect.equals(0, byteArray.length);
-
-  byteArray = new Uint8List(10);
-  Expect.equals(10, byteArray.length);
-  for (int i = 0; i < 10; i++) {
-    Expect.equals(0, byteArray[i]);
-  }
-}
-
-void testCreateClampedUint8ByteArray() {
-  Uint8ClampedList clampedByteArray;
-
-  clampedByteArray = new Uint8ClampedList(0);
-  Expect.isTrue(clampedByteArray is Uint8ClampedList);
-  Expect.isFalse(clampedByteArray is Uint8List);
-  Expect.equals(0, clampedByteArray.length);
-  Expect.equals(0, clampedByteArray.lengthInBytes());
-
-  clampedByteArray = new Uint8ClampedList(10);
-  Expect.equals(10, clampedByteArray.length);
-  for (int i = 0; i < 10; i++) {
-    Expect.equals(0, clampedByteArray[i]);
-  }
-}
-
-void testCreateExternalClampedUint8ByteArray() {
-  List externalClampedByteArray;
-
-  externalClampedByteArray = new Uint8ClampedList.transferable(0);
-  Expect.isTrue(externalClampedByteArray is Uint8ClampedList);
-  Expect.isFalse(externalClampedByteArray is Uint8List);
-  Expect.equals(0, externalClampedByteArray.length);
-  Expect.equals(0, externalClampedByteArray.lengthInBytes());
-
-  externalClampedByteArray = new Uint8ClampedList.transferable(10);
-  Expect.equals(10, externalClampedByteArray.length);
-  for (int i = 0; i < 10; i++) {
-    Expect.equals(0, externalClampedByteArray[i]);
-  }
-
-  externalClampedByteArray[0] = -1;
-  Expect.equals(0, externalClampedByteArray[0]);
-  
-  for (int i = 0; i < 10; i++) {
-    externalClampedByteArray[i] = i + 250;
-  }
-  for (int i = 0; i < 10; i++) {
-    Expect.equals(i + 250 > 255 ? 255 : i + 250, externalClampedByteArray[i]);
-  }
-}
-
-void testUnsignedByteArrayRange(bool check_throws) {
-  Uint8List byteArray;
-  byteArray = new Uint8List(10);
-
-  byteArray[1] = 255;
-  Expect.equals(255, byteArray[1]);
-  byteArray[1] = 0;
-  Expect.equals(0, byteArray[1]);
-
-  for (int i = 0; i < byteArray.length; i++) {
-    byteArray[i] = i;
-  }
-  for (int i = 0; i < byteArray.length; i++) {
-    Expect.equals(i, byteArray[i]);
-  }
-
-  // These should eventually throw.
-  byteArray[1] = 256;
-  byteArray[1] = -1;
-  byteArray[2] = -129;
-  if (check_throws) {
-    Expect.throws(() {
-      byteArray[1] = 1.2;
-    });
-  }
-}
-
-void testClampedUnsignedByteArrayRangeHelper(Uint8ClampedList byteArray,
-                                             bool check_throws) {
-  Uint8ClampedList byteArray;
-  byteArray = new Uint8ClampedList(10);
-
-  byteArray[1] = 255;
-  Expect.equals(255, byteArray[1]);
-  byteArray[1] = 0;
-  Expect.equals(0, byteArray[1]);
-  for (int i = 0; i < byteArray.length; i++) {
-    byteArray[i] = i;
-  }
-  for (int i = 0; i < byteArray.length; i++) {
-    Expect.equals(i, byteArray[i]);
-  }
-
-  // These should eventually throw.
-  byteArray[1] = 256;
-  byteArray[2] = -129;
-  Expect.equals(255, byteArray[1]);
-  Expect.equals(0, byteArray[2]);
-}
-
-void testClampedUnsignedByteArrayRange(bool check_throws) {
-  testClampedUnsignedByteArrayRangeHelper(new Uint8ClampedList(10),
-                                          check_throws);
-}
-
-
-void testExternalClampedUnsignedByteArrayRange(bool check_throws) {
-  testClampedUnsignedByteArrayRangeHelper(new Uint8ClampedList.transferable(10),
-                                          check_throws);
-}
-
-
-void testByteArrayRange(bool check_throws) {
-  Int8List byteArray;
-  byteArray = new Int8List(10);
-  byteArray[1] = 0;
-  Expect.equals(0, byteArray[1]);
-  byteArray[2] = -128;
-  Expect.equals(-128, byteArray[2]);
-  byteArray[3] = 127;
-  Expect.equals(127, byteArray[3]);
-  // This should eventually throw.
-  byteArray[0] = 128;
-  byteArray[4] = -129;
-  if (check_throws) {
-    Expect.throws(() {
-      byteArray[1] = 1.2;
-    });
-  }
-}
-
-void testSetRangeHelper(byteArray) {
-  List<int> list = [10, 11, 12];
-  byteArray.setRange(0, 3, list);
-  for (int i = 0; i < 3; i++) {
-    Expect.equals(10 + i, byteArray[i]);
-  }
-
-  byteArray[0] = 20;
-  byteArray[1] = 21;
-  byteArray[2] = 22;
-  list.setRange(0, 3, byteArray);
-  for (int i = 0; i < 3; i++) {
-    Expect.equals(20 + i, list[i]);
-  }
-
-  byteArray.setRange(1, 2, const [8, 9]);
-  Expect.equals(20, byteArray[0]);
-  Expect.equals(8, byteArray[1]);
-  Expect.equals(9, byteArray[2]);
-}
-
-void testSetRange() {
-  testSetRangeHelper(new Uint8List(3));
-  testSetRangeHelper(new Uint8List.transferable(3));
-  testSetRangeHelper(new Uint8ClampedList(3));
-  testSetRangeHelper(new Uint8ClampedList.transferable(3));
-}
-
-void testIndexOutOfRangeHelper(byteArray) {
-  List<int> list = const [0, 1, 2, 3];
-
-  Expect.throws(() {
-    byteArray.setRange(0, 4, list);
-  });
-
-  Expect.throws(() {
-    byteArray.setRange(3, 1, list);
-  });
-}
-
-void testIndexOutOfRange() {
-  testIndexOutOfRangeHelper(new Uint8List(3));
-  testIndexOutOfRangeHelper(new Uint8List.transferable(3));
-  testIndexOutOfRangeHelper(new Uint8ClampedList(3));
-  testIndexOutOfRangeHelper(new Uint8ClampedList.transferable(3));
-}
-
-void testIndexOfHelper(list) {
-  for (int i = 0; i < list.length; i++) {
-    list[i] = i + 10;
-  }
-  Expect.equals(0, list.indexOf(10));
-  Expect.equals(5, list.indexOf(15));
-  Expect.equals(9, list.indexOf(19));
-  Expect.equals(-1, list.indexOf(20));
-
-  list = new Float32List(10);
-  for (int i = 0; i < list.length; i++) {
-    list[i] = i + 10.0;
-  }
-  Expect.equals(0, list.indexOf(10.0));
-  Expect.equals(5, list.indexOf(15.0));
-  Expect.equals(9, list.indexOf(19.0));
-  Expect.equals(-1, list.indexOf(20.0));
-}
-
-void testIndexOf() {
-  testIndexOfHelper(new Uint8List(10));
-  testIndexOfHelper(new Uint8List.transferable(10));
-  testIndexOfHelper(new Uint8ClampedList(10));
-  testIndexOfHelper(new Uint8ClampedList.transferable(10));
-}
-
-void testSubArrayHelper(list) {
-  var array = list.asByteArray();
-  Expect.equals(0, array.subByteArray(0, 0).lengthInBytes());
-  Expect.equals(0, array.subByteArray(5, 0).lengthInBytes());
-  Expect.equals(0, array.subByteArray(10, 0).lengthInBytes());
-  Expect.equals(0, array.subByteArray(10).lengthInBytes());
-  Expect.equals(0, array.subByteArray(10, null).lengthInBytes());
-  Expect.equals(5, array.subByteArray(0, 5).lengthInBytes());
-  Expect.equals(5, array.subByteArray(5, 5).lengthInBytes());
-  Expect.equals(5, array.subByteArray(5).lengthInBytes());
-  Expect.equals(5, array.subByteArray(5, null).lengthInBytes());
-  Expect.equals(10, array.subByteArray(0, 10).lengthInBytes());
-  Expect.equals(10, array.subByteArray(0).lengthInBytes());
-  Expect.equals(10, array.subByteArray(0, null).lengthInBytes());
-  Expect.equals(10, array.subByteArray().lengthInBytes());
-  testThrowsIndex(function) {
-    Expect.throws(function, (e) => e is RangeError);
-  }
-  testThrowsIndex(() => array.subByteArray(0, -1));
-  testThrowsIndex(() => array.subByteArray(1, -1));
-  testThrowsIndex(() => array.subByteArray(10, -1));
-  testThrowsIndex(() => array.subByteArray(-1, 0));
-  testThrowsIndex(() => array.subByteArray(-1));
-  testThrowsIndex(() => array.subByteArray(-1, null));
-  testThrowsIndex(() => array.subByteArray(11, 0));
-  testThrowsIndex(() => array.subByteArray(11));
-  testThrowsIndex(() => array.subByteArray(11, null));
-  testThrowsIndex(() => array.subByteArray(6, 5));
-
-  bool checkedMode = false;
-  assert(checkedMode = true);
-  if (!checkedMode) {
-    // In checked mode these will necessarily throw a TypeError.
-    Expect.throws(() => array.subByteArray(0, "5"), (e) => e is ArgumentError);
-    Expect.throws(() => array.subByteArray("0", 5), (e) => e is ArgumentError);
-    Expect.throws(() => array.subByteArray("0"), (e) => e is ArgumentError);
-  }
-  Expect.throws(() => array.subByteArray(null), (e) => e is ArgumentError);
-}
-
-
-void testSubArray() {
-  testSubArrayHelper(new Uint8List(10));
-  testSubArrayHelper(new Uint8List.transferable(10));
-  testSubArrayHelper(new Uint8ClampedList(10));
-  testSubArrayHelper(new Uint8ClampedList.transferable(10));
-}
-
-main() {
-  for (int i = 0; i < 2000; i++) {
-    testCreateUint8ByteArray();
-    testCreateClampedUint8ByteArray();
-    testCreateExternalClampedUint8ByteArray();
-    testByteArrayRange(false);
-    testUnsignedByteArrayRange(false);
-    testClampedUnsignedByteArrayRange(false);
-    testExternalClampedUnsignedByteArrayRange(false);
-    testSetRange();
-    testIndexOutOfRange();
-    testIndexOf();
-    testSubArray();
-  }
-  testByteArrayRange(true);
-  testUnsignedByteArrayRange(true);
-  testExternalClampedUnsignedByteArrayRange(true);
-}
-
diff --git a/tests/standalone/byte_array_view_optimized_test.dart b/tests/standalone/byte_array_view_optimized_test.dart
index 2d9f646..9f3b0be 100644
--- a/tests/standalone/byte_array_view_optimized_test.dart
+++ b/tests/standalone/byte_array_view_optimized_test.dart
@@ -7,14 +7,14 @@
 // Library tag to be able to run in html test framework.
 library ByteArrayViewOptimizedTest;
 
-import "dart:scalarlist";
+import "dart:typeddata";
 
 li16(v) => v[0];
 
 main() {
   var a = new Uint8List.transferable(2);
   a[0] = a[1] = 0xff;
-  var b = new Int16List.view(a.asByteArray());
+  var b = new Int16List.view(a.buffer);
   Expect.equals(-1, li16(b));
   for (var i=0; i<10000; i++) li16(b);
   Expect.equals(-1, li16(b));
diff --git a/tests/standalone/debugger/debug_lib.dart b/tests/standalone/debugger/debug_lib.dart
index 0d13f7a..cf244b4 100644
--- a/tests/standalone/debugger/debug_lib.dart
+++ b/tests/standalone/debugger/debug_lib.dart
@@ -7,19 +7,19 @@
 library DartDebugger;
 
 import "dart:io";
+import "dart:math";
 import "dart:utf";
 import "dart:json" as JSON;
 
-// TODO(hausner): need to select a different port number for each
-// test that runs in parallel.
-var debugPort = 5860;
-
 // Whether or not to print debug target process on the console.
 var showDebuggeeOutput = true;
 
 // Whether or not to print the debugger wire messages on the console.
 var verboseWire = false;
 
+// The number of attempts made to find an unused debugger port.
+var retries = 0;
+
 // Class to buffer wire protocol data from debug target and
 // break it down to individual json messages.
 class JsonBuffer {
@@ -323,15 +323,8 @@
   bool shutdownEventSeen = false;
   int isolateId = 0;
 
-  // stdin subscription to allow terminating the test via command-line.
-  var stdinSubscription;
-
   Debugger(this.targetProcess, this.portNumber) {
-    stdinSubscription =
-        stdin.listen((d) {},
-                     onError: (error) => close(killDebugee: true),
-                     onDone: () => close(killDebugee: true));
-
+    stdin.listen((_) {});
     var stdoutStringStream = targetProcess.stdout
         .transform(new StringDecoder())
         .transform(new LineTransformer());
@@ -500,15 +493,12 @@
       for (int i = 0; i < errors.length; i++) print(errors[i]);
     }
     socket.close();
-    stdinSubscription.cancel();
     if (killDebugee) {
       targetProcess.kill();
       print("Target process killed");
     }
     Expect.isTrue(!errorsDetected);
-    stdin.close();
-    stdout.close();
-    stderr.close();
+    exit(errors.length);
   }
 }
 
@@ -518,24 +508,41 @@
   if (options.arguments.contains("--debuggee")) {
     return false;
   }
-  showDebuggeeOutput = options.arguments.contains("--verbose");
+  // The default is to show debugging output.
+  showDebuggeeOutput = !options.arguments.contains("--non-verbose");
   verboseWire = options.arguments.contains("--wire");
+  
+  // Pick a port in the upper half of the port number range.
+  var seed = new DateTime.now().millisecondsSinceEpoch;
+  Random random = new Random(seed);
+  var debugPort = random.nextInt(32000) + 32000;
+  print('using debug port $debugPort ...');
+  ServerSocket.bind('127.0.0.1', debugPort).then((ServerSocket s) {
+      s.close();
+      var targetOpts = [ "--debug:$debugPort" ];
+      if (showDebuggeeOutput) targetOpts.add("--verbose_debug");
+      targetOpts.add(options.script);
+      targetOpts.add("--debuggee");
 
-  var targetOpts = [ "--debug:$debugPort" ];
-  if (showDebuggeeOutput) targetOpts.add("--verbose_debug");
-  targetOpts.add(options.script);
-  targetOpts.add("--debuggee");
-
-  Process.start(options.executable, targetOpts).then((Process process) {
-    print("Debug target process started");
-    process.stdin.close();
-    process.exitCode.then((int exitCode) {
-      Expect.equals(0, exitCode);
-      Expect.equals(0, exitCode);
-      print("Debug target process exited with exit code $exitCode");
+      Process.start(options.executable, targetOpts).then((Process process) {
+        print("Debug target process started");
+        process.stdin.close();
+        process.exitCode.then((int exitCode) {
+          Expect.equals(0, exitCode);
+          print("Debug target process exited with exit code $exitCode");
+        });
+        var debugger = new Debugger(process, debugPort);
+        debugger.runScript(script);
+      });
+    },
+    onError: (e) {
+      if (++retries >= 3) { 
+        print('unable to find unused port: $e');
+        return -1; 
+      } else {
+        // Retry with another random port.
+        RunScript(script);
+      }
     });
-    var debugger = new Debugger(process, debugPort);
-    debugger.runScript(script);
-  });
   return true;
 }
diff --git a/tests/standalone/io/http_client_request_test.dart b/tests/standalone/io/http_client_request_test.dart
index 84e7b2d..b762a78 100644
--- a/tests/standalone/io/http_client_request_test.dart
+++ b/tests/standalone/io/http_client_request_test.dart
@@ -4,7 +4,7 @@
 
 import "dart:io";
 import "dart:isolate";
-import "dart:scalarlist";
+import "dart:typeddata";
 
 void testClientRequest(void handler(request)) {
   HttpServer.bind().then((server) {
diff --git a/tests/standalone/io/http_close_test.dart b/tests/standalone/io/http_close_test.dart
index 056ec0e..43bde37 100644
--- a/tests/standalone/io/http_close_test.dart
+++ b/tests/standalone/io/http_close_test.dart
@@ -9,7 +9,7 @@
 
 import "dart:async";
 import "dart:io";
-import "dart:scalarlist";
+import "dart:typeddata";
 
 
 void testClientAndServerCloseNoListen(int connections) {
diff --git a/tests/standalone/io/http_compression_test.dart b/tests/standalone/io/http_compression_test.dart
index 7720063..ce3f9c9 100644
--- a/tests/standalone/io/http_compression_test.dart
+++ b/tests/standalone/io/http_compression_test.dart
@@ -8,7 +8,7 @@
 // VMOptions=--short_socket_read --short_socket_write
 
 import 'dart:io';
-import 'dart:scalarlist';
+import 'dart:typeddata';
 
 void testServerCompress() {
   void test(List<int> data) {
diff --git a/tests/standalone/io/http_parser_test.dart b/tests/standalone/io/http_parser_test.dart
index cc4cc4d..87abee3 100644
--- a/tests/standalone/io/http_parser_test.dart
+++ b/tests/standalone/io/http_parser_test.dart
@@ -4,7 +4,7 @@
 
 import 'dart:async';
 import 'dart:math';
-import 'dart:scalarlist';
+import 'dart:typeddata';
 import 'dart:isolate';
 import 'dart:uri';
 
diff --git a/tests/standalone/io/http_server_response_test.dart b/tests/standalone/io/http_server_response_test.dart
index be1dfff..db3888f 100644
--- a/tests/standalone/io/http_server_response_test.dart
+++ b/tests/standalone/io/http_server_response_test.dart
@@ -9,7 +9,7 @@
 
 import "dart:async";
 import "dart:io";
-import "dart:scalarlist";
+import "dart:typeddata";
 
 void testServerRequest(void handler(server, request), {int bytes}) {
   HttpServer.bind().then((server) {
diff --git a/tests/standalone/io/web_socket_protocol_processor_test.dart b/tests/standalone/io/web_socket_protocol_processor_test.dart
index 1490e71..c762ae4 100644
--- a/tests/standalone/io/web_socket_protocol_processor_test.dart
+++ b/tests/standalone/io/web_socket_protocol_processor_test.dart
@@ -6,7 +6,7 @@
 import "dart:math";
 import "dart:async";
 import "dart:collection";
-import "dart:scalarlist";
+import "dart:typeddata";
 
 part "../../../sdk/lib/io/http.dart";
 part "../../../sdk/lib/io/buffer_list.dart";
diff --git a/tests/standalone/package/package_test.dart b/tests/standalone/package/package_test.dart
index e55181a..c71d54d 100644
--- a/tests/standalone/package/package_test.dart
+++ b/tests/standalone/package/package_test.dart
@@ -4,10 +4,10 @@
 
 // PackageRoot=none
 
-#library('package_test');
+library package_test;
 
-#import('package:lib1.dart');
-#import('package:shared.dart');
+import 'package:lib1.dart';
+import 'package:shared.dart';
 
 void main() {
   output = 'main';
diff --git a/tests/standalone/package/packages/lib1.dart b/tests/standalone/package/packages/lib1.dart
index 18d0bf8..f5175a2 100644
--- a/tests/standalone/package/packages/lib1.dart
+++ b/tests/standalone/package/packages/lib1.dart
@@ -2,10 +2,10 @@
 // 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('lib1');
+library lib1;
 
-#import('package:shared.dart');
-#import('package:lib2/lib2.dart');
+import 'package:shared.dart';
+import 'package:lib2/lib2.dart';
 
 void lib1() {
   output += '|lib1';
diff --git a/tests/standalone/package/packages/lib2/lib2.dart b/tests/standalone/package/packages/lib2/lib2.dart
index 017d8ae..b649a27 100644
--- a/tests/standalone/package/packages/lib2/lib2.dart
+++ b/tests/standalone/package/packages/lib2/lib2.dart
@@ -2,10 +2,10 @@
 // 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('lib2');
+library lib2;
 
-#import('package:shared.dart');
-#import('package:lib3/sub/lib3.dart');
+import 'package:shared.dart';
+import 'package:lib3/sub/lib3.dart';
 
 void lib2() {
   output += '|lib2';
diff --git a/tests/standalone/package/packages/lib3/sub/lib3.dart b/tests/standalone/package/packages/lib3/sub/lib3.dart
index 91a40a0..16bd99f 100644
--- a/tests/standalone/package/packages/lib3/sub/lib3.dart
+++ b/tests/standalone/package/packages/lib3/sub/lib3.dart
@@ -2,9 +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.
 
-#library('lib3');
+library lib3;
 
-#import('package:shared.dart');
+import 'package:shared.dart';
 
 void lib3() {
   output += '|lib3';
diff --git a/tests/standalone/package/packages/package1.dart b/tests/standalone/package/packages/package1.dart
index 9f1b462..c409ec5 100644
--- a/tests/standalone/package/packages/package1.dart
+++ b/tests/standalone/package/packages/package1.dart
@@ -2,11 +2,11 @@
 // 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("package1");
+library package1;
 
-#import('package2.dart', prefix: 'p1');
-#import('package2.dart', prefix: 'p2');
-#import('package:package2.dart', prefix: 'p3');
+import 'package2.dart' as p1;
+import 'package2.dart' as p2;
+import 'package:package2.dart' as p3;
 
 main() {
   Expect.identical(p1.x, p2.x);
diff --git a/tests/standalone/package/packages/package2.dart b/tests/standalone/package/packages/package2.dart
index 91b51c4..4d31974 100644
--- a/tests/standalone/package/packages/package2.dart
+++ b/tests/standalone/package/packages/package2.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.
 
-#library("package2");
+library package2;
 
 class X {
   const X();
diff --git a/tests/standalone/package/packages/shared.dart b/tests/standalone/package/packages/shared.dart
index c2193c3..5145c42 100644
--- a/tests/standalone/package/packages/shared.dart
+++ b/tests/standalone/package/packages/shared.dart
@@ -2,6 +2,6 @@
 // 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('shared');
+library shared;
 
 var output = '';
diff --git a/tests/standalone/standalone.status b/tests/standalone/standalone.status
index 1c05350..9ca9922 100644
--- a/tests/standalone/standalone.status
+++ b/tests/standalone/standalone.status
@@ -14,7 +14,7 @@
 
 # Fails with a connection refused error on the buildbot.
 # Issue 8232.
-debugger/basic_debugger_test: Pass, Fail
+debugger/basic_debugger_test: Skip
 
 [ $runtime == vm && $checked ]
 # These tests have type errors on purpose.
@@ -27,6 +27,7 @@
 # checked mode with no benefit. Skip.
 io/file_fuzz_test: Skip
 io/directory_fuzz_test: Skip
+io/process_exit_negative_test: Pass, Crash # Issue 9403
 
 [ $runtime == vm && $system == macos ]
 io/regress_7191_test: Pass, Timeout # http://dartbug.com/8091
@@ -61,7 +62,6 @@
 
 # package test issue 7392
 package/package1_test: Fail
-package/package_isolate_test: Fail
 package/package_test: Fail
 
 
diff --git a/tests/standalone/typed_data_test.dart b/tests/standalone/typed_data_test.dart
index 9b31a2a..665e05c 100644
--- a/tests/standalone/typed_data_test.dart
+++ b/tests/standalone/typed_data_test.dart
@@ -218,7 +218,7 @@
 }
 
 void testGetAtIndex(TypedData list, num initial_value) {
-  var bdata = new ByteData.view(list);
+  var bdata = new ByteData.view(list.buffer);
   for (int i = 0; i < bdata.lengthInBytes; i++) {
     Expect.equals(42, bdata.getUint8(i));
     Expect.equals(42, bdata.getInt8(i));
@@ -247,7 +247,7 @@
       if (reinit) list[i] = use_double? 0.0 : 0;
     }
   }
-  var bdata = new ByteData.view(list);
+  var bdata = new ByteData.view(list.buffer);
   for (int i = 0; i < bdata.lengthInBytes; i++) bdata.setUint8(i, 42);
   validate();
   for (int i = 0; i < bdata.lengthInBytes; i++) bdata.setInt8(i, 42);
diff --git a/tools/VERSION b/tools/VERSION
index 77e1b1c..217a1a6 100644
--- a/tools/VERSION
+++ b/tools/VERSION
@@ -1,4 +1,4 @@
 MAJOR 0
 MINOR 4
-BUILD 3
-PATCH 6
+BUILD 4
+PATCH 0
diff --git a/tools/bots/editor.py b/tools/bots/editor.py
index 4e4e02e..80d85d4 100755
--- a/tools/bots/editor.py
+++ b/tools/bots/editor.py
@@ -4,10 +4,20 @@
 # BSD-style license that can be found in the LICENSE file.
 
 import os
+import shutil
 import sys
+import tempfile
 
 import bot
 
+class TempDir(object):
+  def __enter__(self):
+    self._temp_dir = tempfile.mkdtemp('eclipse-workspace')
+    return self._temp_dir
+
+  def __exit__(self, *_):
+    shutil.rmtree(self._temp_dir, ignore_errors = True)
+
 def GetEditorExecutable(mode, arch):
   configuration_dir = mode + arch.upper()
   linux_path = os.path.join('out', configuration_dir, 'editor')
@@ -50,10 +60,11 @@
   for arch in test_architectures:
     editor_executable = GetEditorExecutable('Release', arch)
     with bot.BuildStep('Test Editor %s' % arch):
-      args = [editor_executable, '--test', '--auto-exit']
-      print 'Running: %s' % (' '.join(args))
-      sys.stdout.flush()
-      bot.RunProcess(args)
+      with TempDir() as temp_dir:
+        args = [editor_executable, '--test', '--auto-exit', '-data', temp_dir]
+        print 'Running: %s' % (' '.join(args))
+        sys.stdout.flush()
+        bot.RunProcess(args)
   return 0
 
 if __name__ == '__main__':
diff --git a/tools/bots/pub.py b/tools/bots/pub.py
index f778cad..f9f18ee 100755
--- a/tools/bots/pub.py
+++ b/tools/bots/pub.py
@@ -47,7 +47,7 @@
     print 'Building package-root: %s' % (' '.join(args))
     bot.RunProcess(args)
 
-  bot.RunTest('pub', build_info, ['pub', 'pkg', 'dartdoc'])
+  bot.RunTest('pub', build_info, ['pub', 'pkg', 'dartdoc', 'docs'])
 
 
 if __name__ == '__main__':
diff --git a/tools/create_sdk.py b/tools/create_sdk.py
index 5843aa5..ca7038b 100755
--- a/tools/create_sdk.py
+++ b/tools/create_sdk.py
@@ -38,7 +38,7 @@
 # ......utf/
 # ......scalarlist/
 # ......typeddata/
-# ....pkg/
+# ....packages/
 # ......args/
 # ......intl/
 # ......logging/
@@ -215,20 +215,19 @@
              ignore=ignore_patterns('*.svn', 'doc', '*.py', '*.gypi', '*.sh'))
 
 
-  # Create and copy pkg.
-  PKG = join(SDK_tmp, 'pkg')
-  os.makedirs(PKG)
+  # Create and copy packages.
+  PACKAGES = join(SDK_tmp, 'packages')
+  os.makedirs(PACKAGES)
 
   #
-  # Create and populate pkg/{args, intl, logging, meta, unittest, ...}
+  # Create and populate packages/{args, intl, logging, meta, unittest, ...}
   #
 
   for library in ['args', 'http', 'intl', 'logging', 'meta', 'oauth2', 'pathos',
                   'serialization', 'unittest', 'yaml']:
 
-    copytree(join(HOME, 'pkg', library), join(PKG, library),
-             ignore=ignore_patterns('*.svn', 'doc', 'docs',
-                                    '*.py', '*.gypi', '*.sh', 'packages'))
+    copytree(join(HOME, 'pkg', library, 'lib'), join(PACKAGES, library),
+             ignore=ignore_patterns('*.svn'))
 
   # Create and copy tools.
   UTIL = join(SDK_tmp, 'util')
@@ -275,18 +274,6 @@
   # Copy dart2js/dartdoc/pub.
   CopyDartScripts(HOME, build_dir, SDK_tmp, version)
 
-  # Fix up dartdoc.
-  # TODO(dgrove): Remove this once issue 6619 is fixed.
-  ReplaceInFiles([join(SDK_tmp, 'lib', '_internal', 'dartdoc',
-                       'bin', 'dartdoc.dart'),
-                  join(SDK_tmp, 'lib', '_internal', 'dartdoc',
-                       'lib', 'universe_serializer.dart')], [
-                  ("../../../../../pkg/args/lib/args.dart",
-                   "../../../../pkg/args/lib/args.dart"),
-                  ("../../../../../pkg/pathos/lib/path.dart",
-                   "../../../../pkg/pathos/lib/path.dart"),
-                 ])
-
   # Write the 'version' file
   versionFile = open(os.path.join(SDK_tmp, 'version'), 'w')
   versionFile.write(version + '\n')
diff --git a/tools/dom/docs/bin/docs.dart b/tools/dom/docs/bin/docs.dart
index 6972432..6f39783 100644
--- a/tools/dom/docs/bin/docs.dart
+++ b/tools/dom/docs/bin/docs.dart
@@ -18,10 +18,11 @@
 main() {
   print('Converting HTML docs from $lib_path to $json_path.');
 
-  var anyErrors = convert(lib_path, json_path);
-
-  print('Converted HTML docs ${anyErrors ? "with $anyErrors" : "without"}'
-    ' errors.');
+  convert(lib_path, json_path)
+    .then((bool anyErrors) {
+      print('Converted HTML docs ${anyErrors ? "with": "without"}'
+        ' errors.');
+    });
 }
 
 /**
@@ -29,4 +30,4 @@
  * script.
  */
 Path get scriptDir =>
-    new Path(new Options().script).directoryPath;
\ No newline at end of file
+    new Path(new Options().script).directoryPath;
diff --git a/tools/dom/docs/docs.json b/tools/dom/docs/docs.json
index 084eca4..568e824 100644
--- a/tools/dom/docs/docs.json
+++ b/tools/dom/docs/docs.json
@@ -343,6 +343,30 @@
         " */"
       ]
     },
+    "WorkerContext": {
+      "members": {
+        "webkitRequestFileSystem": [
+          "/**",
+          "   * Access a sandboxed file system of the specified `size`. If `persistent` is",
+          "   * true, the application will request permission from the user to create",
+          "   * lasting storage. This storage cannot be freed without the user's",
+          "   * permission. Returns a [Future] whose value stores a reference to the",
+          "   * sandboxed file system for use. Because the file system is sandboxed,",
+          "   * applications cannot access file systems created in other web pages. ",
+          "   */"
+        ],
+        "webkitRequestFileSystemSync": [
+          "/**",
+          "   * Access a sandboxed file system of the specified `size`. If `persistent` is",
+          "   * true, the application will request permission from the user to create",
+          "   * lasting storage. This storage cannot be freed without the user's",
+          "   * permission. This call will block until a reference to the synchronous file ",
+          "   * system API has been obtained. Because the file system is sandboxed,",
+          "   * applications cannot access file systems created in other web pages. ",
+          "   */"
+        ]
+      }
+    },
     "XMLHttpRequest": {
       "members": {
         "abort": [
diff --git a/tools/dom/docs/docs.status b/tools/dom/docs/docs.status
new file mode 100644
index 0000000..43d96f1
--- /dev/null
+++ b/tools/dom/docs/docs.status
@@ -0,0 +1,7 @@
+# Copyright (c) 2013, 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.
+
+# docs.dart is a tool that only runs on the VM
+[ $compiler == dart2js || $compiler == dart2dart || $compiler == dartc || $runtime == drt || $runtime == dartium ]
+*: Skip
diff --git a/tools/dom/docs/lib/docs.dart b/tools/dom/docs/lib/docs.dart
index 9e89782..1b38913 100644
--- a/tools/dom/docs/lib/docs.dart
+++ b/tools/dom/docs/lib/docs.dart
@@ -1,3 +1,7 @@
+// Copyright (c) 2013, 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 library for extracting the documentation from the various HTML libraries
  * ([dart:html], [dart:svg], [dart:web_audio], [dart:indexed_db]) and saving
@@ -6,9 +10,10 @@
 
 library docs;
 
+import '../../../../sdk/lib/_internal/compiler/implementation/mirrors/dart2js_mirror.dart';
 import '../../../../sdk/lib/_internal/compiler/implementation/mirrors/mirrors.dart';
-import '../../../../sdk/lib/_internal/dartdoc/lib/src/json_serializer.dart';
 import '../../../../sdk/lib/_internal/dartdoc/lib/dartdoc.dart';
+import '../../../../sdk/lib/_internal/dartdoc/lib/src/json_serializer.dart';
 import '../../../../utils/apidoc/lib/metadata.dart';
 import 'dart:async';
 import 'dart:io';
@@ -43,41 +48,39 @@
  *       ...
  *     }
  *
- * Returns `true` if any errors were encountered, `false` otherwise.
+ * Completes to `true` if any errors were encountered, `false` otherwise.
  */
-bool convert(Path libPath, Path jsonPath) {
+Future<bool> convert(Path libPath, Path jsonPath) {
   var paths = <Path>[];
   for (var libraryName in HTML_LIBRARY_NAMES) {
     paths.add(new Path(libraryName));
   }
 
-  // TODO(amouravski): Account for errors in compilation.
-  final compilation = new Compilation.library(paths, libPath, null,
-      ['--preserve-comments']);
-
-  var convertedJson = _generateJsonFromLibraries(compilation);
-
-  var anyErrors = _exportJsonToFile(convertedJson, jsonPath);
-
-  return anyErrors;
+  return analyze(paths, libPath, options: ['--preserve-comments'])
+    .then((MirrorSystem mirrors) {
+      var convertedJson = _generateJsonFromLibraries(mirrors);
+      return _exportJsonToFile(convertedJson, jsonPath);
+    });
 }
 
-bool _exportJsonToFile(Map convertedJson, Path jsonPath) {
-  final jsonFile = new File.fromPath(jsonPath);
-  var writeJson = prettySerialize(convertedJson);
+Future<bool> _exportJsonToFile(Map convertedJson, Path jsonPath) {
+  return new Future.of(() {
+    final jsonFile = new File.fromPath(jsonPath);
+    var writeJson = prettySerialize(convertedJson);
 
-  var outputStream = jsonFile.openOutputStream();
-  outputStream.writeString(writeJson);
-
-  return false;
+    var outputStream = jsonFile.openWrite();
+    outputStream.writeln(writeJson);
+    outputStream.close();
+    return outputStream.done.then((_) => false);
+  });
 }
 
-Map _generateJsonFromLibraries(Compilation compilation) {
+Map _generateJsonFromLibraries(MirrorSystem mirrors) {
   var convertedJson = {};
 
   // Sort the libraries by name (not key).
   var sortedLibraries = new List<LibraryMirror>.from(
-      compilation.mirrors.libraries.values.where(
+      mirrors.libraries.values.where(
           (e) => HTML_LIBRARY_NAMES.indexOf(e.uri.toString()) >= 0))
       ..sort((x, y) =>
         x.uri.toString().toUpperCase().compareTo(
diff --git a/tools/dom/docs/test/docs_test.dart b/tools/dom/docs/test/docs_test.dart
new file mode 100644
index 0000000..e87b2f6
--- /dev/null
+++ b/tools/dom/docs/test/docs_test.dart
@@ -0,0 +1,51 @@
+// Copyright (c) 2013, 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 docs_test;
+
+import 'dart:io';
+
+import 'package:unittest/unittest.dart';
+
+import '../bin/docs.dart';
+import '../lib/docs.dart';
+
+final testJsonPath = scriptDir.append('test.json').canonicalize();
+
+main() {
+  test('Ensure that docs.json is up to date', () {
+    var oldJson = new File.fromPath(json_path);
+    var testJson = new File.fromPath(testJsonPath);
+
+    // We should find a json file where we expect it.
+    expect(oldJson.existsSync(), isTrue);
+
+    // Save the last modified time to check it at the end.
+    var oldJsonModified = oldJson.lastModifiedSync();
+
+    // There should be no test file yet.
+    if (testJson.existsSync()) testJson.deleteSync();
+    expect(testJson.existsSync(), isFalse);
+
+    expect(convert(lib_path, testJsonPath)
+        .then((bool anyErrors) {
+      expect(anyErrors, isFalse);
+
+      // We should have a file now.
+      expect(testJson.existsSync(), isTrue);
+
+      // Ensure that there's nothing different between the new JSON and old.
+      expect(testJson.readAsStringSync(), equals(oldJson.readAsStringSync()));
+
+      // Ensure that the old JSON file didn't actually change.
+      expect(oldJsonModified, equals(oldJson.lastModifiedSync()));
+
+      // Clean up.
+      if (testJson.existsSync()) {
+        testJson.deleteSync();
+      }
+      expect(testJson.existsSync(), isFalse);
+    }), completes);
+  });
+}
diff --git a/tools/dom/scripts/idlnode.py b/tools/dom/scripts/idlnode.py
index f8dc742..006006d 100755
--- a/tools/dom/scripts/idlnode.py
+++ b/tools/dom/scripts/idlnode.py
@@ -333,6 +333,7 @@
 
   def __init__(self, ast):
     IDLNode.__init__(self, ast)
+    self.nullable = self._has(ast, 'Nullable')
     # Search for a 'ScopedName' or any label ending with 'Type'.
     if isinstance(ast, list):
       self.id = self._find_first(ast, 'ScopedName')
diff --git a/tools/dom/scripts/idlrenderer.py b/tools/dom/scripts/idlrenderer.py
index c145ade..aa2e139 100755
--- a/tools/dom/scripts/idlrenderer.py
+++ b/tools/dom/scripts/idlrenderer.py
@@ -141,7 +141,12 @@
       wsp(node.ext_attrs)
       if node.is_read_only:
         w('readonly ')
-      w('attribute %s %s' % (node.type.id, node.id))
+      w('attribute ')
+      w(node.type.id)
+      if (node.type.nullable):
+        w('?')
+      w(' ')
+      w(node.id)
       if node.raises:
         w(' raises (%s)' % node.raises.id)
       else:
@@ -162,7 +167,10 @@
       if node.specials:
         w(node.specials, ' ')
         w(' ')
-      w('%s ' % node.type.id)
+      w(node.type.id)
+      if (node.type.nullable):
+        w('?')
+      w(' ')
       w(node.id)
       w('(')
       w(node.arguments, ', ')
diff --git a/tools/dom/scripts/idlsync.py b/tools/dom/scripts/idlsync.py
index b258908..43c88d7 100755
--- a/tools/dom/scripts/idlsync.py
+++ b/tools/dom/scripts/idlsync.py
@@ -177,26 +177,19 @@
   out.write(readme)
   out.close()
 
+ZIP_ARCHIVE = 'version-control-dirs.zip'
+
 def SaveVersionControlDir(local_path):
-  version_control_dir = os.path.join(local_path, '.git')
-  if not os.path.isdir(version_control_dir):
-    version_control_dir = os.path.join(local_path, '.svn')
-    if not os.path.isdir(version_control_dir):
-      raise '%s is not a git or svn directory' % local_path
-  temp_dir = tempfile.mkdtemp()
-  shutil.move(version_control_dir, temp_dir)
-  return temp_dir
+  RunCommand([
+    'sh', '-c',
+    'find %s -name .svn -or -name .git | zip -r %s -@' % (
+        os.path.relpath(local_path), ZIP_ARCHIVE)
+  ])
 
 
-def RestoreVersionControlDir(local_path, saved_version_control_dir):
-  version_control_dir = os.path.join(saved_version_control_dir, '.git')
-  if not os.path.isdir(version_control_dir):
-    version_control_dir = os.path.join(saved_version_control_dir, '.svn')
-    if not os.path.isdir(version_control_dir):
-      raise 'Failed restoring version control directory'
-  shutil.move(version_control_dir, local_path)
-  shutil.rmtree(saved_version_control_dir)
-
+def RestoreVersionControlDir():
+  RunCommand(['unzip', ZIP_ARCHIVE, '-d', '.'])
+  RunCommand(['rm', ZIP_ARCHIVE])
 
 def ParseOptions():
   parser = optparse.OptionParser()
@@ -225,11 +218,11 @@
       url, latest = GetSvnRevision(deps, component)
       if revision is None:
         revision = latest
-      saved_version_control_dir = SaveVersionControlDir(local_path);
+      SaveVersionControlDir(local_path);
       RefreshFiles(url, revision, remote_path, local_path, depth)
       PruneExtraFiles(local_path)
       GenerateReadme(local_path, readme, url, revision)
-      RestoreVersionControlDir(local_path, saved_version_control_dir);
+      RestoreVersionControlDir();
 
 if __name__ == '__main__':
   main()
diff --git a/tools/dom/scripts/systemnative.py b/tools/dom/scripts/systemnative.py
index b997c41..4bc95a5 100644
--- a/tools/dom/scripts/systemnative.py
+++ b/tools/dom/scripts/systemnative.py
@@ -227,6 +227,7 @@
         self._interface,
         arguments,
         self._interface.id,
+        False,
         'ConstructorRaisesException' in ext_attrs)
 
   def HasSupportCheck(self):
@@ -352,6 +353,7 @@
         attr,
         [],
         attr.type.id,
+        attr.type.nullable,
         attr.get_raises)
 
   def _AddSetter(self, attr, html_name):
@@ -381,6 +383,7 @@
         attr,
         [attr],
         'void',
+        False,
         attr.set_raises)
 
   def AddIndexer(self, element_type):
@@ -524,6 +527,7 @@
         operation,
         arguments,
         operation.type.id,
+        operation.type.nullable,
         operation.raises)
 
   def _GenerateNativeCallback(self,
@@ -533,6 +537,7 @@
       node,
       arguments,
       return_type,
+      return_type_is_nullable,
       raises_dom_exception):
     ext_attrs = node.ext_attrs
 
@@ -581,6 +586,9 @@
     if 'Reflect' in ext_attrs:
       cpp_arguments = [self._GenerateWebCoreReflectionAttributeName(node)]
 
+    if return_type_is_nullable:
+      cpp_arguments = ['isNull']
+
     v8EnabledPerContext = ext_attrs.get('synthesizedV8EnabledPerContext', ext_attrs.get('V8EnabledPerContext'))
     v8EnabledAtRuntime = ext_attrs.get('synthesizedV8EnabledAtRuntime', ext_attrs.get('V8EnabledAtRuntime'))
     assert(not (v8EnabledPerContext and v8EnabledAtRuntime))
@@ -758,8 +766,20 @@
       return_type_info = self._TypeInfo(return_type)
       self._cpp_impl_includes |= set(return_type_info.conversion_includes())
 
+      if return_type_is_nullable:
+        invocation_emitter.Emit(
+          '        bool isNull = false;\n'
+          '        $NATIVE_TYPE result = $FUNCTION_CALL;\n'
+          '        if (isNull)\n'
+          '            return;\n',
+          NATIVE_TYPE=return_type_info.native_type(),
+          FUNCTION_CALL=function_call)
+        value_expression = 'result'
+      else:
+        value_expression = function_call
+
       # Generate to Dart conversion of C++ value.
-      to_dart_conversion = return_type_info.to_dart_conversion(function_call, self._interface.id, ext_attrs)
+      to_dart_conversion = return_type_info.to_dart_conversion(value_expression, self._interface.id, ext_attrs)
       invocation_emitter.Emit(
         '        Dart_Handle returnValue = $TO_DART_CONVERSION;\n'
         '        if (returnValue)\n'
diff --git a/tools/dom/src/Isolates.dart b/tools/dom/src/Isolates.dart
index 467d998..b6b0fb8 100644
--- a/tools/dom/src/Isolates.dart
+++ b/tools/dom/src/Isolates.dart
@@ -63,7 +63,7 @@
 // The receiver is JS.
 class _JsSendPortSync implements SendPortSync {
 
-  num _id;
+  final num _id;
   _JsSendPortSync(this._id);
 
   callSync(var message) {
diff --git a/tools/dom/src/KeyboardEventController.dart b/tools/dom/src/KeyboardEventStream.dart
similarity index 78%
rename from tools/dom/src/KeyboardEventController.dart
rename to tools/dom/src/KeyboardEventStream.dart
index 80e8bf0..48dbdba 100644
--- a/tools/dom/src/KeyboardEventController.dart
+++ b/tools/dom/src/KeyboardEventStream.dart
@@ -5,17 +5,10 @@
 part of html;
 
 /**
- * Works with KeyboardEvent and KeyEvent to determine how to expose information
- * about Key(board)Events. This class functions like an EventListenerList, and
- * provides a consistent interface for the Dart
- * user, despite the fact that a multitude of browsers that have varying
- * keyboard default behavior.
- *
- * This class is very much a work in progress, and we'd love to get information
- * on how we can make this class work with as many international keyboards as
- * possible. Bugs welcome!
+ * Internal class that does the actual calculations to determine keyCode and
+ * charCode for keydown, keypress, and keyup events for all browsers.
  */
-class KeyboardEventController {
+class _KeyboardEventHandler extends EventStreamProvider<KeyEvent> {
   // This code inspired by Closure's KeyHandling library.
   // http://closure-library.googlecode.com/svn/docs/closure_goog_events_keyhandler.js.source.html
 
@@ -23,29 +16,28 @@
    * The set of keys that have been pressed down without seeing their
    * corresponding keyup event.
    */
-  List<KeyboardEvent> _keyDownList;
-
-  /** The set of functions that wish to be notified when a KeyEvent happens. */
-  List<Function> _callbacks;
+  final List<KeyboardEvent> _keyDownList = <KeyboardEvent>[];
 
   /** The type of KeyEvent we are tracking (keyup, keydown, keypress). */
-  String _type;
+  final String _type;
 
   /** The element we are watching for events to happen on. */
-  EventTarget _target;
+  final EventTarget _target;
 
   // The distance to shift from upper case alphabet Roman letters to lower case.
-  final int _ROMAN_ALPHABET_OFFSET = "a".codeUnits[0] - "A".codeUnits[0];
+  static final int _ROMAN_ALPHABET_OFFSET = "a".codeUnits[0] - "A".codeUnits[0];
 
-  StreamSubscription _keyUpSubscription, _keyDownSubscription,
-      _keyPressSubscription;
+  /** Controller to produce KeyEvents for the stream. */
+  final StreamController _controller = new StreamController.broadcast();
+
+  static const _EVENT_TYPE = 'KeyEvent';
 
   /**
    * An enumeration of key identifiers currently part of the W3C draft for DOM3
    * and their mappings to keyCodes.
    * http://www.w3.org/TR/DOM-Level-3-Events/keyset.html#KeySet-Set
    */
-  static Map<String, int> _keyIdentifier = {
+  static const Map<String, int> _keyIdentifier = const {
     'Up': KeyCode.UP,
     'Down': KeyCode.DOWN,
     'Left': KeyCode.LEFT,
@@ -71,53 +63,48 @@
     'Insert': KeyCode.INSERT
   };
 
-  /** Named constructor to add an onKeyPress event listener to our handler. */
-  KeyboardEventController.keypress(EventTarget target) {
-    _KeyboardEventController(target, 'keypress');
+  /** Return a stream for KeyEvents for the specified target. */
+  Stream<KeyEvent> forTarget(EventTarget e, {bool useCapture: false}) {
+    return new _KeyboardEventHandler.initializeAllEventListeners(
+        _type, e).stream;
   }
 
-  /** Named constructor to add an onKeyUp event listener to our handler. */
-  KeyboardEventController.keyup(EventTarget target) {
-    _KeyboardEventController(target, 'keyup');
-  }
-
-  /** Named constructor to add an onKeyDown event listener to our handler. */
-  KeyboardEventController.keydown(EventTarget target) {
-    _KeyboardEventController(target, 'keydown');
+  /**
+   * Accessor to the stream associated with a particular KeyboardEvent
+   * EventTarget.
+   *
+   * [forTarget] must be called to initialize this stream to listen to a
+   * particular EventTarget.
+   */
+  Stream<KeyEvent> get stream {
+    if(_target != null) {
+      return _controller.stream;
+    } else {
+      throw new StateError("Not initialized. Call forTarget to access a stream "
+          "initialized with a particular EventTarget.");
+    }
   }
 
   /**
    * General constructor, performs basic initialization for our improved
    * KeyboardEvent controller.
    */
-  _KeyboardEventController(EventTarget target, String type) {
-    _callbacks = [];
-    _type = type;
-    _target = target;
+  _KeyboardEventHandler(this._type) :
+    _target = null, super(_EVENT_TYPE) {
   }
 
   /**
    * Hook up all event listeners under the covers so we can estimate keycodes
    * and charcodes when they are not provided.
    */
-  void _initializeAllEventListeners() {
-    _keyDownList = [];
-    if (_keyDownSubscription == null) {
-      _keyDownSubscription = Element.keyDownEvent.forTarget(
-          _target, useCapture: true).listen(processKeyDown);
-      _keyPressSubscription = Element.keyPressEvent.forTarget(
-          _target, useCapture: true).listen(processKeyUp);
-      _keyUpSubscription = Element.keyUpEvent.forTarget(
-          _target, useCapture: true).listen(processKeyPress);
-    }
-  }
-
-  /** Add a callback that wishes to be notified when a KeyEvent occurs. */
-  void add(void callback(KeyEvent)) {
-    if (_callbacks.length == 0) {
-      _initializeAllEventListeners();
-    }
-    _callbacks.add(callback);
+  _KeyboardEventHandler.initializeAllEventListeners(this._type, this._target) : 
+    super(_EVENT_TYPE) {
+    Element.keyDownEvent.forTarget(_target, useCapture: true).listen(
+        processKeyDown);
+    Element.keyPressEvent.forTarget(_target, useCapture: true).listen(
+        processKeyPress);
+    Element.keyUpEvent.forTarget(_target, useCapture: true).listen(
+        processKeyUp);
   }
 
   /**
@@ -125,31 +112,8 @@
    * occurred.
    */
   bool _dispatch(KeyEvent event) {
-    if (event.type == _type) {
-      // Make a copy of the listeners in case a callback gets removed while
-      // dispatching from the list.
-      List callbacksCopy = new List.from(_callbacks);
-      for(var callback in callbacksCopy) {
-        callback(event);
-      }
-    }
-  }
-
-  /** Remove the given callback from the listeners list. */
-  void remove(void callback(KeyEvent)) {
-    var index = _callbacks.indexOf(callback);
-    if (index != -1) {
-      _callbacks.removeAt(index);
-    }
-    if (_callbacks.length == 0) {
-      // If we have no listeners, don't bother keeping track of keypresses.
-      _keyDownSubscription.cancel();
-      _keyDownSubscription = null;
-      _keyPressSubscription.cancel();
-      _keyPressSubscription = null;
-      _keyUpSubscription.cancel();
-      _keyUpSubscription = null;
-    }
+    if (event.type == _type)
+      _controller.add(event);
   }
 
   /** Determine if caps lock is one of the currently depressed keys. */
@@ -337,7 +301,7 @@
          _keyDownList.last.keyCode == KeyCode.ALT && !e.altKey ||
          Device.userAgent.contains('Mac') &&
          _keyDownList.last.keyCode == KeyCode.META && !e.metaKey)) {
-      _keyDownList = [];
+      _keyDownList.clear();
     }
 
     var event = new KeyEvent(e);
@@ -397,8 +361,7 @@
       }
     }
     if (toRemove != null) {
-      _keyDownList =
-          _keyDownList.where((element) => element != toRemove).toList();
+      _keyDownList.removeWhere((element) => element == toRemove);
     } else if (_keyDownList.length > 0) {
       // This happens when we've reached some international keyboard case we
       // haven't accounted for or we haven't correctly eliminated all browser
@@ -408,3 +371,34 @@
     _dispatch(e);
   }
 }
+
+
+/**
+ * Records KeyboardEvents that occur on a particular element, and provides a
+ * stream of outgoing KeyEvents with cross-browser consistent keyCode and
+ * charCode values despite the fact that a multitude of browsers that have
+ * varying keyboard default behavior.
+ *
+ * Example usage:
+ *
+ *     KeyboardEventStream.onKeyDown(document.body).listen(
+ *         keydownHandlerTest);
+ *
+ * This class is very much a work in progress, and we'd love to get information
+ * on how we can make this class work with as many international keyboards as
+ * possible. Bugs welcome!
+ */
+class KeyboardEventStream {
+
+  /** Named constructor to produce a stream for onKeyPress events. */
+  static Stream<KeyEvent> onKeyPress(EventTarget target) =>
+      new _KeyboardEventHandler('keypress').forTarget(target);
+
+  /** Named constructor to produce a stream for onKeyUp events. */
+  static Stream<KeyEvent> onKeyUp(EventTarget target) =>
+      new _KeyboardEventHandler('keyup').forTarget(target);
+
+  /** Named constructor to produce a stream for onKeyDown events. */
+  static Stream<KeyEvent> onKeyDown(EventTarget target) =>
+    new _KeyboardEventHandler('keydown').forTarget(target);
+}
diff --git a/tools/dom/src/Microtask.dart b/tools/dom/src/Microtask.dart
index 4b811e4..2599bdf 100644
--- a/tools/dom/src/Microtask.dart
+++ b/tools/dom/src/Microtask.dart
@@ -12,7 +12,7 @@
  */
 abstract class _MicrotaskScheduler {
   bool _nextMicrotaskFrameScheduled = false;
-  _MicrotaskCallback _callback;
+  final _MicrotaskCallback _callback;
 
   _MicrotaskScheduler(this._callback);
 
diff --git a/tools/dom/src/Timer.dart b/tools/dom/src/Timer.dart
index 01048ea..27e7b90 100644
--- a/tools/dom/src/Timer.dart
+++ b/tools/dom/src/Timer.dart
@@ -28,3 +28,36 @@
   timer = new _Timer(() { canceller(id); });
   return timer;
 };
+
+class _PureIsolateTimer implements Timer {
+  final ReceivePort _port = new ReceivePort();
+  SendPort _sendPort; // Effectively final.
+
+  _PureIsolateTimer(int milliSeconds, callback, repeating) {
+    _sendPort = _port.toSendPort();
+    _port.receive((msg, replyTo) {
+      assert(msg == _TIMER_PING);
+      assert(replyTo == _HELPER_ISOLATE_PORT);
+      callback(this);
+      if (!repeating) _cancel();
+    });
+    _HELPER_ISOLATE_PORT.then((port) {
+      port.send([_NEW_TIMER, milliSeconds, repeating], _sendPort);
+    });
+  }
+
+  void cancel() {
+    _cancel();
+    _HELPER_ISOLATE_PORT.then((port) {
+      port.send([_CANCEL_TIMER], _sendPort);
+    });
+  }
+
+  void _cancel() {
+    _port.close();
+  }
+}
+
+get _pureIsolateTimerFactoryClosure =>
+    ((int milliSeconds, void callback(Timer time), bool repeating) =>
+        new _PureIsolateTimer(milliSeconds, callback, repeating));
diff --git a/tools/dom/src/chrome/chrome.dart b/tools/dom/src/chrome/chrome.dart
index 303e2fc..221ee5e 100644
--- a/tools/dom/src/chrome/chrome.dart
+++ b/tools/dom/src/chrome/chrome.dart
@@ -9,7 +9,7 @@
   /*
    * JS Variable
    */
-  Object _jsObject;
+  final Object _jsObject;
 
   /*
    * Members
diff --git a/tools/dom/src/chrome/utils.dart b/tools/dom/src/chrome/utils.dart
index eddc6a4..57a6b68 100644
--- a/tools/dom/src/chrome/utils.dart
+++ b/tools/dom/src/chrome/utils.dart
@@ -33,7 +33,7 @@
   /*
    * JS Object Representation
    */
-  Object _jsObject;
+  final Object _jsObject;
 }
 
 /**
@@ -170,12 +170,12 @@
   /*
    * JS Object Representation
    */
-  Object _jsObject;
+  final Object _jsObject;
 
   /*
    * Number of arguments the callback takes.
    */
-  int _callbackArity;
+  final int _callbackArity;
 
   /*
    * Private constructor
diff --git a/tools/dom/src/dart2js_DOMImplementation.dart b/tools/dom/src/dart2js_DOMImplementation.dart
index adb5f27..051df51 100644
--- a/tools/dom/src/dart2js_DOMImplementation.dart
+++ b/tools/dom/src/dart2js_DOMImplementation.dart
@@ -9,7 +9,7 @@
   // Private window.  Note, this is a window in another frame, so it
   // cannot be typed as "Window" as its prototype is not patched
   // properly.  Its fields and methods can only be accessed via JavaScript.
-  var _window;
+  final _window;
 
   // Fields.
   HistoryBase get history =>
diff --git a/tools/dom/src/dart2js_KeyEvent.dart b/tools/dom/src/dart2js_KeyEvent.dart
index 5686b61..5a0a133 100644
--- a/tools/dom/src/dart2js_KeyEvent.dart
+++ b/tools/dom/src/dart2js_KeyEvent.dart
@@ -3,6 +3,9 @@
  * inconsistencies, and also provide both keyCode and charCode information
  * for all key events (when such information can be determined).
  *
+ * KeyEvent tries to provide a higher level, more polished keyboard event
+ * information on top of the "raw" [KeyboardEvent].
+ *
  * This class is very much a work in progress, and we'd love to get information
  * on how we can make this class work with as many international keyboards as
  * possible. Bugs welcome!
@@ -41,7 +44,7 @@
   /** Accessor to the underlying altKey value is the parent event. */
   bool get _realAltKey => JS('int', '#.altKey', _parent);
 
-  /** Construct a KeyEvent with [parent] as event we're emulating. */
+  /** Construct a KeyEvent with [parent] as the event we're emulating. */
   KeyEvent(KeyboardEvent parent) {
     _parent = parent;
     _shadowAltKey = _realAltKey;
@@ -49,6 +52,18 @@
     _shadowKeyCode = _realKeyCode;
   }
 
+  // TODO(efortuna): If KeyEvent is sufficiently successful that we want to make
+  // it the default keyboard event handling, move these methods over to Element.
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyDownEvent =
+    new _KeyboardEventHandler('keydown');
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyUpEvent =
+    new _KeyboardEventHandler('keyup');
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyPressEvent =
+    new _KeyboardEventHandler('keypress');
+
   /** True if the altGraphKey is pressed during this event. */
   bool get altGraphKey => _parent.altGraphKey;
   bool get bubbles => _parent.bubbles;
diff --git a/tools/dom/src/dartium_KeyEvent.dart b/tools/dom/src/dartium_KeyEvent.dart
index 5be90c9..8f129a1 100644
--- a/tools/dom/src/dartium_KeyEvent.dart
+++ b/tools/dom/src/dartium_KeyEvent.dart
@@ -3,6 +3,9 @@
  * inconsistencies, and also provide both keyCode and charCode information
  * for all key events (when such information can be determined).
  *
+ * KeyEvent tries to provide a higher level, more polished keyboard event
+ * information on top of the "raw" [KeyboardEvent].
+ *
  * This class is very much a work in progress, and we'd love to get information
  * on how we can make this class work with as many international keyboards as
  * possible. Bugs welcome!
@@ -41,7 +44,7 @@
   /** Accessor to the underlying altKey value is the parent event. */
   bool get _realAltKey => _parent.altKey;
 
-  /** Construct a KeyEvent with [parent] as event we're emulating. */
+  /** Construct a KeyEvent with [parent] as the event we're emulating. */
   KeyEvent(KeyboardEvent parent) {
     _parent = parent;
     _shadowAltKey = _realAltKey;
@@ -49,6 +52,16 @@
     _shadowKeyCode = _realKeyCode;
   }
 
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyDownEvent =
+    new _KeyboardEventHandler('keydown');
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyUpEvent =
+    new _KeyboardEventHandler('keyup');
+  /** Accessor to provide a stream of KeyEvents on the desired target. */
+  static EventStreamProvider<KeyEvent> keyPressEvent =
+    new _KeyboardEventHandler('keypress');
+
   /** True if the altGraphKey is pressed during this event. */
   bool get altGraphKey => _parent.altGraphKey;
   bool get bubbles => _parent.bubbles;
diff --git a/tools/dom/src/native_DOMImplementation.dart b/tools/dom/src/native_DOMImplementation.dart
index 94ba076..8bcab03 100644
--- a/tools/dom/src/native_DOMImplementation.dart
+++ b/tools/dom/src/native_DOMImplementation.dart
@@ -31,6 +31,18 @@
     return result;
   }
 
+  static int convertCanvasElementGetContextMap(Map map) {
+    int result = 0;
+    if (map['alpha'] == true) result |= 0x01;
+    if (map['depth'] == true) result |= 0x02;
+    if (map['stencil'] == true) result |= 0x4;
+    if (map['antialias'] == true) result |= 0x08;
+    if (map['premultipliedAlpha'] == true) result |= 0x10;
+    if (map['preserveDrawingBuffer'] == true) result |= 0x20;
+
+    return result;
+  }
+
   static void populateMap(Map result, List list) {
     for (int i = 0; i < list.length; i += 2) {
       result[list[i]] = list[i + 1];
@@ -46,9 +58,8 @@
   }
 
   static window() native "Utils_window";
-  static print(String message) native "Utils_print";
   static forwardingPrint(String message) native "Utils_forwardingPrint";
-  static SendPort spawnDomFunctionImpl(Function topLevelFunction) native "Utils_spawnDomFunction";
+  static void spawnDomFunction(Function topLevelFunction, int replyTo) native "Utils_spawnDomFunction";
   static int _getNewIsolateId() native "Utils_getNewIsolateId";
   static bool shadowRootSupported(Document document) native "Utils_shadowRootSupported";
 }
@@ -120,12 +131,41 @@
   bool get isEmpty => Maps.isEmpty(this);
 }
 
-get _printClosure => (s) {
-  try {
-    window.console.log(s);
-  } catch (_) {
-    _Utils.print(s);
-  }
+final Future<SendPort> _HELPER_ISOLATE_PORT =
+    spawnDomFunction(_helperIsolateMain);
+
+final _TIMER_REGISTRY = new Map<SendPort, Timer>();
+
+const _NEW_TIMER = 'NEW_TIMER';
+const _CANCEL_TIMER = 'CANCEL_TIMER';
+const _TIMER_PING = 'TIMER_PING';
+const _PRINT = 'PRINT';
+
+_helperIsolateMain() {
+  port.receive((msg, replyTo) {
+    final cmd = msg[0];
+    if (cmd == _NEW_TIMER) {
+      final duration = new Duration(milliseconds: msg[1]);
+      bool periodic = msg[2];
+      final callback = () { replyTo.send(_TIMER_PING); };
+      _TIMER_REGISTRY[replyTo] = periodic ?
+          new Timer.periodic(duration, callback) :
+          new Timer(duration, callback);
+    } else if (cmd == _CANCEL_TIMER) {
+      _TIMER_REGISTRY.remove(replyTo).cancel();
+    } else if (cmd == _PRINT) {
+      final message = msg[1];
+      // TODO(antonm): we need somehow identify those isolates.
+      print('[From isolate] $message');
+    }
+  });
+}
+
+final _printClosure = window.console.log;
+final _pureIsolatePrintClosure = (s) {
+  _HELPER_ISOLATE_PORT.then((sendPort) {
+    sendPort.send([_PRINT, s]);
+  });
 };
 
 final _forwardingPrintClosure = _Utils.forwardingPrint;
diff --git a/tools/dom/src/native_DOMPublic.dart b/tools/dom/src/native_DOMPublic.dart
index 3d224713..5044945 100644
--- a/tools/dom/src/native_DOMPublic.dart
+++ b/tools/dom/src/native_DOMPublic.dart
@@ -5,7 +5,17 @@
 part of html;
 
 // This API is exploratory.
-spawnDomFunction(Function topLevelFunction) => _Utils.spawnDomFunctionImpl(topLevelFunction);
+Future<SendPort> spawnDomFunction(Function topLevelFunction) {
+  final completer = new Completer<SendPort>();
+  final port = new ReceivePort();
+  port.receive((result, _) {
+    completer.complete(result);
+    port.close();
+  });
+  // TODO: SendPort.hashCode is ugly way to access port id.
+  _Utils.spawnDomFunction(topLevelFunction, port.toSendPort().hashCode);
+  return completer.future;
+}
 
 // testRunner implementation.
 // FIXME: provide a separate lib for testRunner.
diff --git a/tools/dom/templates/html/dart2js/html_dart2js.darttemplate b/tools/dom/templates/html/dart2js/html_dart2js.darttemplate
index 6a3521e..18c1ee2 100644
--- a/tools/dom/templates/html/dart2js/html_dart2js.darttemplate
+++ b/tools/dom/templates/html/dart2js/html_dart2js.darttemplate
@@ -32,7 +32,7 @@
 part '$AUXILIARY_DIR/CssClassSet.dart';
 part '$AUXILIARY_DIR/EventListener.dart';
 part '$AUXILIARY_DIR/EventStreamProvider.dart';
-part '$AUXILIARY_DIR/KeyboardEventController.dart';
+part '$AUXILIARY_DIR/KeyboardEventStream.dart';
 part '$AUXILIARY_DIR/KeyCode.dart';
 part '$AUXILIARY_DIR/KeyLocation.dart';
 part '$AUXILIARY_DIR/KeyName.dart';
diff --git a/tools/dom/templates/html/dartium/html_dartium.darttemplate b/tools/dom/templates/html/dartium/html_dartium.darttemplate
index daaf025..b512499 100644
--- a/tools/dom/templates/html/dartium/html_dartium.darttemplate
+++ b/tools/dom/templates/html/dartium/html_dartium.darttemplate
@@ -30,7 +30,7 @@
 part '$AUXILIARY_DIR/CssClassSet.dart';
 part '$AUXILIARY_DIR/EventListener.dart';
 part '$AUXILIARY_DIR/EventStreamProvider.dart';
-part '$AUXILIARY_DIR/KeyboardEventController.dart';
+part '$AUXILIARY_DIR/KeyboardEventStream.dart';
 part '$AUXILIARY_DIR/KeyCode.dart';
 part '$AUXILIARY_DIR/KeyLocation.dart';
 part '$AUXILIARY_DIR/KeyName.dart';
diff --git a/tools/test.dart b/tools/test.dart
index 9a23cfa..218f996 100755
--- a/tools/test.dart
+++ b/tools/test.dart
@@ -57,7 +57,6 @@
     new Path('tests/compiler/dart2js_foreign'),
     new Path('tests/compiler/dart2js_native'),
     new Path('tests/corelib'),
-    new Path('tests/dom'),
     new Path('tests/html'),
     new Path('tests/isolate'),
     new Path('tests/json'),
@@ -68,7 +67,10 @@
     new Path('utils/tests/css'),
     new Path('utils/tests/peg'),
     new Path('utils/tests/pub'),
+    // TODO(amouravski): move these to tests/ once they no longer rely on weird
+    // dependencies.
     new Path('sdk/lib/_internal/dartdoc'),
+    new Path('tools/dom/docs'),
 ];
 
 void testConfigurations(List<Map> configurations) {
diff --git a/tools/testing/dart/test_options.dart b/tools/testing/dart/test_options.dart
index a7f7983..d751ab4 100644
--- a/tools/testing/dart/test_options.dart
+++ b/tools/testing/dart/test_options.dart
@@ -452,8 +452,9 @@
     }
     if (!validRuntimes.contains(config['runtime'])) {
       isValid = false;
-      print("Warning: combination of ${config['compiler']} and "
-          "${config['runtime']} is invalid. Skipping this combination.");
+      print("Warning: combination of compiler '${config['compiler']}' and "
+          "runtime '${config['runtime']}' is invalid. "
+          "Skipping this combination.");
     }
     if ((config['runtime'] == 'ie9' || config['runtime'] == 'ie10') &&
         Platform.operatingSystem != 'windows') {
diff --git a/tools/testing/dart/test_progress.dart b/tools/testing/dart/test_progress.dart
index 72da366..7733217 100644
--- a/tools/testing/dart/test_progress.dart
+++ b/tools/testing/dart/test_progress.dart
@@ -429,10 +429,8 @@
     if (_failedTests > 0) {
       // We may have printed many failure logs, so reprint the summary data.
       _printProgress();
-      print('');
     }
-    stdout.close();
-    stderr.close();
+    print('');
   }
 
   void _printStartProgress(TestCase test) => _printProgress();
diff --git a/tools/testing/dart/test_suite.dart b/tools/testing/dart/test_suite.dart
index cb9c96f..4246405 100644
--- a/tools/testing/dart/test_suite.dart
+++ b/tools/testing/dart/test_suite.dart
@@ -1298,9 +1298,13 @@
    *     // OtherScripts=file1.dart file2.dart
    *
    *   - You can indicate whether a test is treated as a web-only test by
-   *   using an explicit import to the dart:html library:
+   *   using an explicit import to a part of the the dart:html library:
    *
-   *     #import('dart:html');
+   *     import 'dart:html';
+   *     import 'dart:web_audio';
+   *     import 'dart:indexed_db';
+   *     import 'dart:svg';
+   *     import 'dart:web_sql';
    *
    *   Most tests are not web tests, but can (and will be) wrapped within
    *   another script file to test them also on browser environments (e.g.
@@ -1349,7 +1353,8 @@
     RegExp isolateStubsRegExp = new RegExp(r"// IsolateStubs=(.*)");
     // TODO(gram) Clean these up once the old directives are not supported.
     RegExp domImportRegExp =
-        new RegExp(r"^[#]?import.*dart:html", multiLine: true);
+        new RegExp(r"^[#]?import.*dart:(html|web_audio|indexed_db|svg|web_sql)",
+        multiLine: true);
     RegExp libraryDefinitionRegExp =
         new RegExp(r"^[#]?library[\( ]", multiLine: true);
     RegExp sourceOrImportRegExp =
@@ -1503,8 +1508,11 @@
 
       // Using stderr.writeString to avoid breaking dartc/junit_tests
       // which parses the output of the --list option.
-      stderr.writeln(
-          "Warning: deprecated @dynamic-type-error tag used in $filePath");
+
+      // Removed the print below. Tracking of this should be done in the bug
+      // and not in the developer's terminals.
+      // stderr.writeln(
+      //    "Warning: deprecated @dynamic-type-error tag used in $filePath");
     }
 
     return {
diff --git a/utils/apidoc/apidoc.gyp b/utils/apidoc/apidoc.gyp
index 8c6cc70..2500ed0 100644
--- a/utils/apidoc/apidoc.gyp
+++ b/utils/apidoc/apidoc.gyp
@@ -47,6 +47,7 @@
           ],
           'action': [
             '<(PRODUCT_DIR)/<(EXECUTABLE_PREFIX)dart<(EXECUTABLE_SUFFIX)',
+            '--package-root=<(PRODUCT_DIR)/packages/',
             'apidoc.dart',
             '--out=<(PRODUCT_DIR)/api_docs',
             '--version=<!@(["python", "../../tools/print_version.py"])',
@@ -58,11 +59,12 @@
             '--exclude-lib=http',
             '--exclude-lib=oauth2',
             '--exclude-lib=pathos',
+            '--exclude-lib=scheduled_test',
+            '--exclude-lib=stack_trace',
             '--exclude-lib=webdriver',
             '--exclude-lib=yaml',
             '--include-lib=matcher',
             '--include-lib=mock',
-            '--include-lib=scheduled_test',
           ],
           'message': 'Running apidoc: <(_action)',
         },
diff --git a/utils/pub/command_lish.dart b/utils/pub/command_lish.dart
index 2de62a8..c2f2529 100644
--- a/utils/pub/command_lish.dart
+++ b/utils/pub/command_lish.dart
@@ -9,9 +9,10 @@
 import 'dart:json';
 import 'dart:uri';
 
-import '../../pkg/args/lib/args.dart';
-import '../../pkg/http/lib/http.dart' as http;
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:args/args.dart';
+import 'package:http/http.dart' as http;
+import 'package:pathos/path.dart' as path;
+
 import 'directory_tree.dart';
 import 'exit_codes.dart' as exit_codes;
 import 'git.dart' as git;
diff --git a/utils/pub/command_uploader.dart b/utils/pub/command_uploader.dart
index 6541653..977415b 100644
--- a/utils/pub/command_uploader.dart
+++ b/utils/pub/command_uploader.dart
@@ -8,8 +8,9 @@
 import 'dart:io';
 import 'dart:uri';
 
-import '../../pkg/args/lib/args.dart';
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:args/args.dart';
+import 'package:pathos/path.dart' as path;
+
 import 'entrypoint.dart';
 import 'exit_codes.dart' as exit_codes;
 import 'http.dart';
diff --git a/utils/pub/directory_tree.dart b/utils/pub/directory_tree.dart
index 8829655..25f83f0 100644
--- a/utils/pub/directory_tree.dart
+++ b/utils/pub/directory_tree.dart
@@ -5,7 +5,8 @@
 /// A simple library for rendering a list of files as a directory tree.
 library directory_tree;
 
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
+
 import 'log.dart' as log;
 
 /// Draws a directory tree for the given list of files. Given a list of files
diff --git a/utils/pub/entrypoint.dart b/utils/pub/entrypoint.dart
index 2b02f02..95790d3 100644
--- a/utils/pub/entrypoint.dart
+++ b/utils/pub/entrypoint.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import 'io.dart';
 import 'lock_file.dart';
diff --git a/utils/pub/git_source.dart b/utils/pub/git_source.dart
index 986c48e..1193892 100644
--- a/utils/pub/git_source.dart
+++ b/utils/pub/git_source.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import 'git.dart' as git;
 import 'io.dart';
diff --git a/utils/pub/hosted_source.dart b/utils/pub/hosted_source.dart
index bb4345c..4d6626f 100644
--- a/utils/pub/hosted_source.dart
+++ b/utils/pub/hosted_source.dart
@@ -9,9 +9,8 @@
 import 'dart:json' as json;
 import 'dart:uri';
 
-// TODO(nweiz): Make this import better.
-import '../../pkg/http/lib/http.dart' as http;
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:http/http.dart' as http;
+import 'package:pathos/path.dart' as path;
 
 import 'http.dart';
 import 'io.dart';
diff --git a/utils/pub/http.dart b/utils/pub/http.dart
index 59fb586..dadc4b1 100644
--- a/utils/pub/http.dart
+++ b/utils/pub/http.dart
@@ -9,8 +9,8 @@
 import 'dart:io';
 import 'dart:json' as json;
 
-// TODO(nweiz): Make this import better.
-import '../../pkg/http/lib/http.dart' as http;
+import 'package:http/http.dart' as http;
+
 import 'io.dart';
 import 'log.dart' as log;
 import 'oauth2.dart' as oauth2;
diff --git a/utils/pub/io.dart b/utils/pub/io.dart
index 59172c8..4dcbf5d 100644
--- a/utils/pub/io.dart
+++ b/utils/pub/io.dart
@@ -11,14 +11,14 @@
 import 'dart:json';
 import 'dart:uri';
 
-import '../../pkg/pathos/lib/path.dart' as path;
-import '../../pkg/http/lib/http.dart' show ByteStream;
+import 'package:pathos/path.dart' as path;
+import 'package:http/http.dart' show ByteStream;
 import 'error_group.dart';
 import 'exit_codes.dart' as exit_codes;
 import 'log.dart' as log;
 import 'utils.dart';
 
-export '../../pkg/http/lib/http.dart' show ByteStream;
+export 'package:http/http.dart' show ByteStream;
 
 /// Returns whether or not [entry] is nested somewhere within [dir]. This just
 /// performs a path comparison; it doesn't look at the actual filesystem.
diff --git a/utils/pub/lock_file.dart b/utils/pub/lock_file.dart
index 594e523..2f39161 100644
--- a/utils/pub/lock_file.dart
+++ b/utils/pub/lock_file.dart
@@ -5,12 +5,14 @@
 library lock_file;
 
 import 'dart:json' as json;
+
+import 'package:yaml/yaml.dart';
+
 import 'io.dart';
 import 'package.dart';
 import 'source_registry.dart';
 import 'utils.dart';
 import 'version.dart';
-import '../../pkg/yaml/lib/yaml.dart';
 
 /// A parsed and validated `pubspec.lock` file.
 class LockFile {
@@ -97,9 +99,10 @@
 
     // TODO(nweiz): Serialize using the YAML library once it supports
     // serialization. For now, we use JSON, since it's a subset of YAML anyway.
-    return '''
-        # Generated by pub. See: http://pub.dartlang.org/doc/glossary.html#lockfile
-         ${json.stringify({'packages': packagesObj})}
-        ''';
+    return
+        '# Generated by pub\n'
+        '# See http://pub.dartlang.org/doc/glossary.html#lockfile\n'
+        '\n'
+        '${json.stringify({'packages': packagesObj})}\n';
   }
 }
diff --git a/utils/pub/oauth2.dart b/utils/pub/oauth2.dart
index 69364d3..ced3ed4 100644
--- a/utils/pub/oauth2.dart
+++ b/utils/pub/oauth2.dart
@@ -8,9 +8,8 @@
 import 'dart:io';
 import 'dart:uri';
 
-// TODO(nweiz): Make this a "package:" URL, or something nicer than this.
-import '../../pkg/oauth2/lib/oauth2.dart';
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:oauth2/oauth2.dart';
+import 'package:pathos/path.dart' as path;
 
 import 'http.dart';
 import 'io.dart';
@@ -19,7 +18,7 @@
 import 'system_cache.dart';
 import 'utils.dart';
 
-export '../../pkg/oauth2/lib/oauth2.dart';
+export 'package:oauth2/oauth2.dart';
 
 /// The pub client's OAuth2 identifier.
 final _identifier = '818368855108-8grd2eg9tj9f38os6f1urbcvsq399u8n.apps.'
diff --git a/utils/pub/package.dart b/utils/pub/package.dart
index b7c2f99..1bc7445 100644
--- a/utils/pub/package.dart
+++ b/utils/pub/package.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import 'io.dart';
 import 'pubspec.dart';
diff --git a/utils/pub/path_source.dart b/utils/pub/path_source.dart
index 8b3b7a5..3b433a1 100644
--- a/utils/pub/path_source.dart
+++ b/utils/pub/path_source.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import 'log.dart' as log;
 
diff --git a/utils/pub/pub.dart b/utils/pub/pub.dart
index c2fb8f9..5f52a53 100644
--- a/utils/pub/pub.dart
+++ b/utils/pub/pub.dart
@@ -9,8 +9,8 @@
 import 'dart:io';
 import 'dart:math';
 
-import '../../pkg/args/lib/args.dart';
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:args/args.dart';
+import 'package:pathos/path.dart' as path;
 
 import 'command_help.dart';
 import 'command_install.dart';
diff --git a/utils/pub/pubspec.dart b/utils/pub/pubspec.dart
index f2d34a2..de3f155 100644
--- a/utils/pub/pubspec.dart
+++ b/utils/pub/pubspec.dart
@@ -4,8 +4,8 @@
 
 library pubspec;
 
-import '../../pkg/yaml/lib/yaml.dart';
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:yaml/yaml.dart';
+import 'package:pathos/path.dart' as path;
 
 import 'io.dart';
 import 'package.dart';
diff --git a/utils/pub/sdk.dart b/utils/pub/sdk.dart
index 59eea86..7f6b149 100644
--- a/utils/pub/sdk.dart
+++ b/utils/pub/sdk.dart
@@ -7,7 +7,7 @@
 
 import 'dart:io';
 
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import 'io.dart';
 import 'log.dart' as log;
diff --git a/utils/pub/sdk/pub b/utils/pub/sdk/pub
index b5a33c4..c732f16 100755
--- a/utils/pub/sdk/pub
+++ b/utils/pub/sdk/pub
@@ -8,4 +8,4 @@
 BIN_DIR="$(cd "${0%/*}" ; pwd -P)"
 DART_SDK="$(cd "${BIN_DIR%/*}" ; pwd -P)"
 
-exec "$BIN_DIR"/dart "$DART_SDK"/util/pub/pub.dart $@
+exec "$BIN_DIR"/dart --package-root="$DART_SDK"/packages/ "$DART_SDK"/util/pub/pub.dart $@
diff --git a/utils/pub/sdk/pub.bat b/utils/pub/sdk/pub.bat
index a3d9441..e41b02b 100644
--- a/utils/pub/sdk/pub.bat
+++ b/utils/pub/sdk/pub.bat
@@ -11,4 +11,6 @@
 :: Does the string have a trailing slash? If so, remove it.
 if %SCRIPTPATH:~-1%==\ set SCRIPTPATH=%SCRIPTPATH:~0,-1%
 
-"%SCRIPTPATH%\dart.exe" "%SCRIPTPATH%\..\util\pub\pub.dart" %*
+:: The trailing forward slash in --package-root is required because of issue
+:: 9499.
+"%SCRIPTPATH%\dart.exe" --package-root="%SCRIPTPATH%\..\packages/" "%SCRIPTPATH%\..\util\pub\pub.dart" %*
diff --git a/utils/pub/source.dart b/utils/pub/source.dart
index 1180967..109b5b2 100644
--- a/utils/pub/source.dart
+++ b/utils/pub/source.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import 'io.dart';
 import 'package.dart';
diff --git a/utils/pub/system_cache.dart b/utils/pub/system_cache.dart
index 1b30ea8..4c0e176 100644
--- a/utils/pub/system_cache.dart
+++ b/utils/pub/system_cache.dart
@@ -7,7 +7,7 @@
 import 'dart:io';
 import 'dart:async';
 
-import '../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import 'git_source.dart';
 import 'hosted_source.dart';
diff --git a/utils/pub/validator/compiled_dartdoc.dart b/utils/pub/validator/compiled_dartdoc.dart
index 3ab5c34..b139869 100644
--- a/utils/pub/validator/compiled_dartdoc.dart
+++ b/utils/pub/validator/compiled_dartdoc.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../entrypoint.dart';
 import '../io.dart';
diff --git a/utils/pub/validator/directory.dart b/utils/pub/validator/directory.dart
index cabf45d..032c0d1 100644
--- a/utils/pub/validator/directory.dart
+++ b/utils/pub/validator/directory.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../entrypoint.dart';
 import '../io.dart';
diff --git a/utils/pub/validator/lib.dart b/utils/pub/validator/lib.dart
index 9a5b9d0..c31b071 100644
--- a/utils/pub/validator/lib.dart
+++ b/utils/pub/validator/lib.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../entrypoint.dart';
 import '../io.dart';
diff --git a/utils/pub/validator/license.dart b/utils/pub/validator/license.dart
index 29fb318..6cd623b 100644
--- a/utils/pub/validator/license.dart
+++ b/utils/pub/validator/license.dart
@@ -6,7 +6,7 @@
 
 import 'dart:async';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../entrypoint.dart';
 import '../io.dart';
diff --git a/utils/pub/validator/name.dart b/utils/pub/validator/name.dart
index c953d78..2dc93e5 100644
--- a/utils/pub/validator/name.dart
+++ b/utils/pub/validator/name.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../entrypoint.dart';
 import '../io.dart';
diff --git a/utils/pub/validator/utf8_readme.dart b/utils/pub/validator/utf8_readme.dart
index edfdde3..145ac86 100644
--- a/utils/pub/validator/utf8_readme.dart
+++ b/utils/pub/validator/utf8_readme.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:utf';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../entrypoint.dart';
 import '../io.dart';
diff --git a/utils/tests/pub/command_line_config.dart b/utils/tests/pub/command_line_config.dart
index df4a28a..f05f931 100644
--- a/utils/tests/pub/command_line_config.dart
+++ b/utils/tests/pub/command_line_config.dart
@@ -6,8 +6,8 @@
 
 import 'dart:io';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
-import '../../../pkg/unittest/lib/unittest.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:unittest/unittest.dart';
 import '../../pub/utils.dart';
 
 /// Gets a "special" string (ANSI escape or Unicode). On Windows, returns
diff --git a/utils/tests/pub/descriptor.dart b/utils/tests/pub/descriptor.dart
index 957299c..17d352a 100644
--- a/utils/tests/pub/descriptor.dart
+++ b/utils/tests/pub/descriptor.dart
@@ -5,17 +5,17 @@
 /// Pub-specific scheduled_test descriptors.
 library descriptor;
 
-import '../../../pkg/oauth2/lib/oauth2.dart' as oauth2;
-import '../../../pkg/scheduled_test/lib/scheduled_server.dart';
-import '../../../pkg/scheduled_test/lib/scheduled_test.dart';
-import '../../../pkg/scheduled_test/lib/descriptor.dart';
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:scheduled_test/scheduled_server.dart';
+import 'package:scheduled_test/scheduled_test.dart';
+import 'package:scheduled_test/descriptor.dart';
 
 import '../../pub/utils.dart';
 import 'descriptor/git.dart';
 import 'descriptor/tar.dart';
 import 'test_pub.dart';
 
-export '../../../pkg/scheduled_test/lib/descriptor.dart';
+export 'package:scheduled_test/descriptor.dart';
 export 'descriptor/git.dart';
 export 'descriptor/tar.dart';
 
diff --git a/utils/tests/pub/descriptor/git.dart b/utils/tests/pub/descriptor/git.dart
index 5e4b3b2..5ef6e98 100644
--- a/utils/tests/pub/descriptor/git.dart
+++ b/utils/tests/pub/descriptor/git.dart
@@ -6,9 +6,9 @@
 
 import 'dart:async';
 
-import '../../../../pkg/pathos/lib/path.dart' as path;
-import '../../../../pkg/scheduled_test/lib/scheduled_test.dart';
-import '../../../../pkg/scheduled_test/lib/descriptor.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_test.dart';
+import 'package:scheduled_test/descriptor.dart';
 
 import '../../../pub/git.dart' as git;
 
diff --git a/utils/tests/pub/descriptor/tar.dart b/utils/tests/pub/descriptor/tar.dart
index ef9b1f3..18af2b3 100644
--- a/utils/tests/pub/descriptor/tar.dart
+++ b/utils/tests/pub/descriptor/tar.dart
@@ -7,9 +7,9 @@
 import 'dart:io';
 import 'dart:async';
 
-import '../../../../pkg/pathos/lib/path.dart' as path;
-import '../../../../pkg/scheduled_test/lib/scheduled_test.dart';
-import '../../../../pkg/scheduled_test/lib/descriptor.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_test.dart';
+import 'package:scheduled_test/descriptor.dart';
 
 import '../../../pub/io.dart';
 import '../../../pub/utils.dart';
diff --git a/utils/tests/pub/dev_dependency_test.dart b/utils/tests/pub/dev_dependency_test.dart
index 8934302..1e37807 100644
--- a/utils/tests/pub/dev_dependency_test.dart
+++ b/utils/tests/pub/dev_dependency_test.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 '../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import 'descriptor.dart' as d;
 import 'test_pub.dart';
diff --git a/utils/tests/pub/directory_tree_test.dart b/utils/tests/pub/directory_tree_test.dart
index 8a45a6f..5adf785 100644
--- a/utils/tests/pub/directory_tree_test.dart
+++ b/utils/tests/pub/directory_tree_test.dart
@@ -4,7 +4,8 @@
 
 library lock_file_test;
 
-import '../../../pkg/unittest/lib/unittest.dart';
+import 'package:unittest/unittest.dart';
+
 import '../../pub/directory_tree.dart';
 
 main() {
diff --git a/utils/tests/pub/error_group_test.dart b/utils/tests/pub/error_group_test.dart
index b3e0ba0..e7aa477 100644
--- a/utils/tests/pub/error_group_test.dart
+++ b/utils/tests/pub/error_group_test.dart
@@ -6,7 +6,8 @@
 
 import 'dart:async';
 
-import '../../../pkg/unittest/lib/unittest.dart';
+import 'package:unittest/unittest.dart';
+
 import '../../pub/error_group.dart';
 import '../../pub/utils.dart';
 
diff --git a/utils/tests/pub/install/broken_symlink_test.dart b/utils/tests/pub/install/broken_symlink_test.dart
index 76540dc..7b627b2 100644
--- a/utils/tests/pub/install/broken_symlink_test.dart
+++ b/utils/tests/pub/install/broken_symlink_test.dart
@@ -6,7 +6,7 @@
 
 import 'dart:io';
 
-import '../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../descriptor.dart' as d;
 import '../test_pub.dart';
diff --git a/utils/tests/pub/install/git/check_out_with_trailing_slash_test.dart b/utils/tests/pub/install/git/check_out_with_trailing_slash_test.dart
index 64c4534..2b1bb1c 100644
--- a/utils/tests/pub/install/git/check_out_with_trailing_slash_test.dart
+++ b/utils/tests/pub/install/git/check_out_with_trailing_slash_test.dart
@@ -6,7 +6,7 @@
 
 import 'dart:io';
 
-import '../../../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../../descriptor.dart' as d;
 import '../../test_pub.dart';
diff --git a/utils/tests/pub/install/git/lock_version_test.dart b/utils/tests/pub/install/git/lock_version_test.dart
index ad6c92a..205b6ea 100644
--- a/utils/tests/pub/install/git/lock_version_test.dart
+++ b/utils/tests/pub/install/git/lock_version_test.dart
@@ -6,8 +6,8 @@
 
 import 'dart:io';
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
-import '../../../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../../../../pub/io.dart';
 import '../../descriptor.dart' as d;
diff --git a/utils/tests/pub/install/hosted/repair_cache_test.dart b/utils/tests/pub/install/hosted/repair_cache_test.dart
index 5af5ab6..7d808d6 100644
--- a/utils/tests/pub/install/hosted/repair_cache_test.dart
+++ b/utils/tests/pub/install/hosted/repair_cache_test.dart
@@ -4,7 +4,7 @@
 
 library pub_tests;
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../../../../pub/io.dart';
 import '../../descriptor.dart' as d;
diff --git a/utils/tests/pub/install/hosted/stay_locked_test.dart b/utils/tests/pub/install/hosted/stay_locked_test.dart
index df7cf87..d765af5 100644
--- a/utils/tests/pub/install/hosted/stay_locked_test.dart
+++ b/utils/tests/pub/install/hosted/stay_locked_test.dart
@@ -6,8 +6,8 @@
 
 import 'dart:io';
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
-import '../../../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../../../../pub/io.dart';
 import '../../descriptor.dart' as d;
diff --git a/utils/tests/pub/install/path/absolute_path_test.dart b/utils/tests/pub/install/path/absolute_path_test.dart
index 9e991c4..dfe0492 100644
--- a/utils/tests/pub/install/path/absolute_path_test.dart
+++ b/utils/tests/pub/install/path/absolute_path_test.dart
@@ -2,8 +2,8 @@
 // for details. All rights reserved. Use of this source code is governed by a
 // BSD-style license that can be found in the LICENSE d.file.
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
-import '../../../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../../../../pub/io.dart';
 import '../../descriptor.dart' as d;
diff --git a/utils/tests/pub/install/path/absolute_symlink_test.dart b/utils/tests/pub/install/path/absolute_symlink_test.dart
index 7ecb0e5..392b09b 100644
--- a/utils/tests/pub/install/path/absolute_symlink_test.dart
+++ b/utils/tests/pub/install/path/absolute_symlink_test.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 d.file.
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../../../../pub/exit_codes.dart' as exit_codes;
 import '../../descriptor.dart' as d;
diff --git a/utils/tests/pub/install/path/no_pubspec_test.dart b/utils/tests/pub/install/path/no_pubspec_test.dart
index 37620fa..4553861 100644
--- a/utils/tests/pub/install/path/no_pubspec_test.dart
+++ b/utils/tests/pub/install/path/no_pubspec_test.dart
@@ -4,8 +4,8 @@
 
 import 'dart:io';
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
-import '../../../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../../descriptor.dart' as d;
 import '../../test_pub.dart';
diff --git a/utils/tests/pub/install/path/nonexistent_dir_test.dart b/utils/tests/pub/install/path/nonexistent_dir_test.dart
index 53009cf..d93da4a 100644
--- a/utils/tests/pub/install/path/nonexistent_dir_test.dart
+++ b/utils/tests/pub/install/path/nonexistent_dir_test.dart
@@ -4,8 +4,8 @@
 
 import 'dart:io';
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
-import '../../../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../../../../pub/exit_codes.dart' as exit_codes;
 import '../../descriptor.dart' as d;
diff --git a/utils/tests/pub/install/path/path_is_file_test.dart b/utils/tests/pub/install/path/path_is_file_test.dart
index 75fc8ba..9635575 100644
--- a/utils/tests/pub/install/path/path_is_file_test.dart
+++ b/utils/tests/pub/install/path/path_is_file_test.dart
@@ -2,8 +2,8 @@
 // for details. All rights reserved. Use of this source code is governed by a
 // BSD-style license that can be found in the LICENSE d.file.
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
-import '../../../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../../../../pub/exit_codes.dart' as exit_codes;
 import '../../descriptor.dart' as d;
diff --git a/utils/tests/pub/install/path/relative_path_test.dart b/utils/tests/pub/install/path/relative_path_test.dart
index 4474562..59dcd12 100644
--- a/utils/tests/pub/install/path/relative_path_test.dart
+++ b/utils/tests/pub/install/path/relative_path_test.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 d.file.
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../../../../pub/exit_codes.dart' as exit_codes;
 import '../../descriptor.dart' as d;
diff --git a/utils/tests/pub/install/path/relative_symlink_test.dart b/utils/tests/pub/install/path/relative_symlink_test.dart
index eef8570..e5917af 100644
--- a/utils/tests/pub/install/path/relative_symlink_test.dart
+++ b/utils/tests/pub/install/path/relative_symlink_test.dart
@@ -4,7 +4,7 @@
 
 import 'dart:io';
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../../../../pub/exit_codes.dart' as exit_codes;
 import '../../descriptor.dart' as d;
diff --git a/utils/tests/pub/install/path/shared_dependency_symlink_test.dart b/utils/tests/pub/install/path/shared_dependency_symlink_test.dart
index b192be3..9cb3a9b 100644
--- a/utils/tests/pub/install/path/shared_dependency_symlink_test.dart
+++ b/utils/tests/pub/install/path/shared_dependency_symlink_test.dart
@@ -4,7 +4,7 @@
 
 import 'dart:io';
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../../descriptor.dart' as d;
 import '../../test_pub.dart';
diff --git a/utils/tests/pub/install/path/shared_dependency_test.dart b/utils/tests/pub/install/path/shared_dependency_test.dart
index d425112..65e7992 100644
--- a/utils/tests/pub/install/path/shared_dependency_test.dart
+++ b/utils/tests/pub/install/path/shared_dependency_test.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 d.file.
 
-import '../../../../../pkg/pathos/lib/path.dart' as path;
+import 'package:pathos/path.dart' as path;
 
 import '../../descriptor.dart' as d;
 import '../../test_pub.dart';
diff --git a/utils/tests/pub/install/pub_install_test.dart b/utils/tests/pub/install/pub_install_test.dart
index f927b54..37bc1c1 100644
--- a/utils/tests/pub/install/pub_install_test.dart
+++ b/utils/tests/pub/install/pub_install_test.dart
@@ -6,8 +6,8 @@
 
 import 'dart:io';
 
-import '../../../../pkg/pathos/lib/path.dart' as path;
-import '../../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../../../pub/io.dart';
 import '../descriptor.dart' as d;
diff --git a/utils/tests/pub/install/relative_symlink_test.dart b/utils/tests/pub/install/relative_symlink_test.dart
index 5791999..aeb0a2a 100644
--- a/utils/tests/pub/install/relative_symlink_test.dart
+++ b/utils/tests/pub/install/relative_symlink_test.dart
@@ -6,7 +6,7 @@
 
 import 'dart:io';
 
-import '../../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../descriptor.dart' as d;
 import '../test_pub.dart';
diff --git a/utils/tests/pub/io_test.dart b/utils/tests/pub/io_test.dart
index 2ebf55c..585d068 100644
--- a/utils/tests/pub/io_test.dart
+++ b/utils/tests/pub/io_test.dart
@@ -6,8 +6,8 @@
 
 import 'dart:io';
 
-import '../../../pkg/pathos/lib/path.dart' as path;
-import '../../../pkg/unittest/lib/unittest.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:unittest/unittest.dart';
 
 import '../../pub/io.dart';
 import '../../pub/utils.dart';
diff --git a/utils/tests/pub/lock_file_test.dart b/utils/tests/pub/lock_file_test.dart
index cd57bd1..715cff6 100644
--- a/utils/tests/pub/lock_file_test.dart
+++ b/utils/tests/pub/lock_file_test.dart
@@ -4,8 +4,9 @@
 
 library lock_file_test;
 
-import '../../../pkg/unittest/lib/unittest.dart';
-import '../../../pkg/yaml/lib/yaml.dart';
+import 'package:unittest/unittest.dart';
+import 'package:yaml/yaml.dart';
+
 import '../../pub/lock_file.dart';
 import '../../pub/package.dart';
 import '../../pub/source.dart';
diff --git a/utils/tests/pub/oauth2_test.dart b/utils/tests/pub/oauth2_test.dart
index 0b2772b..dd35a9e 100644
--- a/utils/tests/pub/oauth2_test.dart
+++ b/utils/tests/pub/oauth2_test.dart
@@ -8,10 +8,10 @@
 import 'dart:json' as json;
 import 'dart:uri';
 
-import '../../../pkg/http/lib/http.dart' as http;
-import '../../../pkg/scheduled_test/lib/scheduled_process.dart';
-import '../../../pkg/scheduled_test/lib/scheduled_test.dart';
-import '../../../pkg/scheduled_test/lib/scheduled_server.dart';
+import 'package:http/http.dart' as http;
+import 'package:scheduled_test/scheduled_process.dart';
+import 'package:scheduled_test/scheduled_test.dart';
+import 'package:scheduled_test/scheduled_server.dart';
 
 import '../../pub/io.dart';
 import '../../pub/utils.dart';
diff --git a/utils/tests/pub/pub.status b/utils/tests/pub/pub.status
index a33ef1c..f57559f 100644
--- a/utils/tests/pub/pub.status
+++ b/utils/tests/pub/pub.status
@@ -14,3 +14,4 @@
 
 [ $system == windows ]
 io_test: Fail # Issue 7505
+install/hosted/fail_gracefully_on_url_resolve_test: Pass, Fail # Issue 9503
diff --git a/utils/tests/pub/pub_cache_test.dart b/utils/tests/pub/pub_cache_test.dart
index 0dc1d38..ce4ce84 100644
--- a/utils/tests/pub/pub_cache_test.dart
+++ b/utils/tests/pub/pub_cache_test.dart
@@ -7,7 +7,7 @@
 import 'dart:io';
 import 'dart:json' as json;
 
-import '../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../../pub/io.dart';
 import 'descriptor.dart' as d;
diff --git a/utils/tests/pub/pub_lish_test.dart b/utils/tests/pub/pub_lish_test.dart
index 8b38f2e8..065e8ab 100644
--- a/utils/tests/pub/pub_lish_test.dart
+++ b/utils/tests/pub/pub_lish_test.dart
@@ -7,8 +7,8 @@
 import 'dart:io';
 import 'dart:json' as json;
 
-import '../../../pkg/scheduled_test/lib/scheduled_test.dart';
-import '../../../pkg/scheduled_test/lib/scheduled_server.dart';
+import 'package:scheduled_test/scheduled_test.dart';
+import 'package:scheduled_test/scheduled_server.dart';
 
 import '../../pub/exit_codes.dart' as exit_codes;
 import '../../pub/io.dart';
diff --git a/utils/tests/pub/pub_test.dart b/utils/tests/pub/pub_test.dart
index 49d7063..7e8e349 100644
--- a/utils/tests/pub/pub_test.dart
+++ b/utils/tests/pub/pub_test.dart
@@ -6,7 +6,7 @@
 
 import 'dart:io';
 
-import '../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:scheduled_test/scheduled_test.dart';
 
 import 'descriptor.dart' as d;
 import 'test_pub.dart';
diff --git a/utils/tests/pub/pub_uploader_test.dart b/utils/tests/pub/pub_uploader_test.dart
index f065cf0..5413f1d 100644
--- a/utils/tests/pub/pub_uploader_test.dart
+++ b/utils/tests/pub/pub_uploader_test.dart
@@ -7,9 +7,9 @@
 import 'dart:io';
 import 'dart:json' as json;
 
-import '../../../pkg/scheduled_test/lib/scheduled_process.dart';
-import '../../../pkg/scheduled_test/lib/scheduled_server.dart';
-import '../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:scheduled_test/scheduled_process.dart';
+import 'package:scheduled_test/scheduled_server.dart';
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../../pub/io.dart';
 import '../../pub/utils.dart';
diff --git a/utils/tests/pub/pubspec_test.dart b/utils/tests/pub/pubspec_test.dart
index 8b40664..a52aab9 100644
--- a/utils/tests/pub/pubspec_test.dart
+++ b/utils/tests/pub/pubspec_test.dart
@@ -4,13 +4,14 @@
 
 library pubspec_test;
 
-import '../../../pkg/unittest/lib/unittest.dart';
-import 'test_pub.dart';
+import 'package:unittest/unittest.dart';
+
 import '../../pub/pubspec.dart';
 import '../../pub/source.dart';
 import '../../pub/source_registry.dart';
 import '../../pub/utils.dart';
 import '../../pub/version.dart';
+import 'test_pub.dart';
 
 class MockSource extends Source {
   final String name = "mock";
diff --git a/utils/tests/pub/real_version_test.dart b/utils/tests/pub/real_version_test.dart
index 0d1882c..e42fedc 100644
--- a/utils/tests/pub/real_version_test.dart
+++ b/utils/tests/pub/real_version_test.dart
@@ -6,9 +6,9 @@
 
 import 'dart:io';
 
+import 'package:pathos/path.dart' as path;
+import 'package:unittest/unittest.dart';
 import 'test_pub.dart';
-import '../../../pkg/pathos/lib/path.dart' as path;
-import '../../../pkg/unittest/lib/unittest.dart';
 
 main() {
   initConfig();
diff --git a/utils/tests/pub/sdk_constraint_test.dart b/utils/tests/pub/sdk_constraint_test.dart
index db6c769..7a8c87e 100644
--- a/utils/tests/pub/sdk_constraint_test.dart
+++ b/utils/tests/pub/sdk_constraint_test.dart
@@ -4,7 +4,7 @@
 
 library check_sdk_test;
 
-import '../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:scheduled_test/scheduled_test.dart';
 
 import 'descriptor.dart' as d;
 import "test_pub.dart";
diff --git a/utils/tests/pub/test_pub.dart b/utils/tests/pub/test_pub.dart
index bf3722b..156f616 100644
--- a/utils/tests/pub/test_pub.dart
+++ b/utils/tests/pub/test_pub.dart
@@ -16,15 +16,14 @@
 import 'dart:uri';
 import 'dart:utf';
 
-import '../../../pkg/http/lib/testing.dart';
-import '../../../pkg/oauth2/lib/oauth2.dart' as oauth2;
-import '../../../pkg/pathos/lib/path.dart' as path;
-import '../../../pkg/scheduled_test/lib/scheduled_process.dart';
-import '../../../pkg/scheduled_test/lib/scheduled_server.dart';
-import '../../../pkg/scheduled_test/lib/scheduled_test.dart';
-import '../../../pkg/yaml/lib/yaml.dart';
+import 'package:http/testing.dart';
+import 'package:oauth2/oauth2.dart' as oauth2;
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_process.dart';
+import 'package:scheduled_test/scheduled_server.dart';
+import 'package:scheduled_test/scheduled_test.dart';
+import 'package:yaml/yaml.dart';
 
-import '../../lib/file_system.dart' as fs;
 import '../../pub/entrypoint.dart';
 // TODO(rnystrom): Using "gitlib" as the prefix here is ugly, but "git" collides
 // with the git descriptor method. Maybe we should try to clean up the top level
@@ -341,9 +340,10 @@
   }
 
   // Find the main pub entrypoint.
-  var pubPath = fs.joinPaths(testDirectory, '../../pub/pub.dart');
+  var pubPath = path.join(testDirectory, '..', '..', 'pub', 'pub.dart');
 
-  var dartArgs = ['--checked', pubPath, '--trace'];
+  var dartArgs = ['--package-root=$_packageRoot/', '--checked', pubPath,
+      '--trace'];
   dartArgs.addAll(args);
 
   if (tokenEndpoint == null) tokenEndpoint = new Future.immediate(null);
@@ -365,6 +365,22 @@
       description: args.isEmpty ? 'pub' : 'pub ${args.first}');
 }
 
+/// Whether pub is running from within the Dart SDK, as opposed to from the Dart
+/// source repository.
+bool get _runningFromSdk => path.dirname(relativeToPub('..')) == 'util';
+
+// TODO(nweiz): use the built-in mechanism for accessing this once it exists
+// (issue 9119).
+/// The path to the `packages` directory from which pub loads its dependencies.
+String get _packageRoot {
+  if (_runningFromSdk) {
+    return path.absolute(relativeToPub(path.join('..', '..', 'packages')));
+  } else {
+    return path.absolute(path.join(
+        path.dirname(new Options().executable), '..', '..', 'packages'));
+  }
+}
+
 /// Skips the current test if Git is not installed. This validates that the
 /// current test is running on a buildbot in which case we expect git to be
 /// installed. If we are not running on the buildbot, we will instead see if
diff --git a/utils/tests/pub/update/pub_update_test.dart b/utils/tests/pub/update/pub_update_test.dart
index 997f145..8242d88 100644
--- a/utils/tests/pub/update/pub_update_test.dart
+++ b/utils/tests/pub/update/pub_update_test.dart
@@ -6,7 +6,7 @@
 
 import 'dart:io';
 
-import '../../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../descriptor.dart' as d;
 import '../test_pub.dart';
diff --git a/utils/tests/pub/validator_test.dart b/utils/tests/pub/validator_test.dart
index 9b3b583..409a757 100644
--- a/utils/tests/pub/validator_test.dart
+++ b/utils/tests/pub/validator_test.dart
@@ -9,10 +9,10 @@
 import 'dart:json' as json;
 import 'dart:math' as math;
 
-import '../../../pkg/http/lib/http.dart' as http;
-import '../../../pkg/http/lib/testing.dart';
-import '../../../pkg/pathos/lib/path.dart' as path;
-import '../../../pkg/scheduled_test/lib/scheduled_test.dart';
+import 'package:http/http.dart' as http;
+import 'package:http/testing.dart';
+import 'package:pathos/path.dart' as path;
+import 'package:scheduled_test/scheduled_test.dart';
 
 import '../../pub/entrypoint.dart';
 import '../../pub/io.dart';
diff --git a/utils/tests/pub/version_solver_test.dart b/utils/tests/pub/version_solver_test.dart
index bdec057b..835139a3 100644
--- a/utils/tests/pub/version_solver_test.dart
+++ b/utils/tests/pub/version_solver_test.dart
@@ -7,7 +7,7 @@
 import 'dart:async';
 import 'dart:io';
 
-import '../../../pkg/unittest/lib/unittest.dart';
+import 'package:unittest/unittest.dart';
 
 import '../../pub/lock_file.dart';
 import '../../pub/package.dart';
diff --git a/utils/tests/pub/version_test.dart b/utils/tests/pub/version_test.dart
index 7543298..5e3fb08 100644
--- a/utils/tests/pub/version_test.dart
+++ b/utils/tests/pub/version_test.dart
@@ -4,7 +4,7 @@
 
 library version_test;
 
-import '../../../pkg/unittest/lib/unittest.dart';
+import 'package:unittest/unittest.dart';
 import 'test_pub.dart';
 import '../../pub/utils.dart';
 import '../../pub/version.dart';