Revert "[dart2wasm] Use DataView in JS typed arrays"

This reverts commit b9b7de14e0b2871a8a6f2f2a0d0c1d236b8c4fe1.

Reason for revert: Dart to Engine rolls are failing, please see
https://github.com/flutter/engine/runs/18494538711

Original change's description:
> [dart2wasm] Use DataView in JS typed arrays
>
> Refcator JS typed array classes to store JS `DataView`s (instead of JS
> typed array with the matching type), and use V8's new optimized
> `DataView` imports.
>
> Brings JS typed array class performance from unusable to reasonable
> levels. In `SkeletalAnimation` benchmark:
>
> - Before: 1444 us.
> - After: 101 us.
>
> Future work:
>
> - Make immutable classes extend the mutable ones. This will allow `[]`
>   calls to be always inlined in JSCM.
>
> - Move list mixin applications from the base class to implementation
>   classes. This will allow members like `elementAt`, `forEach` etc. to
>   have direct calls to other methods of the same class.
>
> - Try adding a `length` field to avoid JS calls in bounds checks.
>
> Change-Id: Ief6165fe9c4a825072077db820b105c4fca30dce
> Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/328920
> Reviewed-by: Aske Simon Christensen <askesc@google.com>
> Commit-Queue: Ömer Ağacan <omersa@google.com>

Change-Id: Iba46cfc409805bcd6f86bcc52a06ed8d54eea671
No-Presubmit: true
No-Tree-Checks: true
No-Try: true
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/335026
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Siva Annamalai <asiva@google.com>
Bot-Commit: Rubber Stamper <rubber-stamper@appspot.gserviceaccount.com>
diff --git a/pkg/dart2wasm/lib/class_info.dart b/pkg/dart2wasm/lib/class_info.dart
index 873f1b6..1667dc0 100644
--- a/pkg/dart2wasm/lib/class_info.dart
+++ b/pkg/dart2wasm/lib/class_info.dart
@@ -264,6 +264,7 @@
   final Set<String> jsCompatibilityTypes = {
     "JSStringImpl",
     "JSArrayBufferImpl",
+    "JSArrayBufferViewImpl",
     "JSDataViewImpl",
     "JSInt8ArrayImpl",
     "JSUint8ArrayImpl",
diff --git a/pkg/dart2wasm/lib/intrinsics.dart b/pkg/dart2wasm/lib/intrinsics.dart
index 99b606a..7b65cd1 100644
--- a/pkg/dart2wasm/lib/intrinsics.dart
+++ b/pkg/dart2wasm/lib/intrinsics.dart
@@ -357,38 +357,21 @@
               b.i32_ne();
               return w.NumType.i32;
             default:
-              throw 'Unknown WasmI32 member $name';
+              throw 'Unknown i32 conversion to $receiverType';
           }
         case w.NumType.i64:
-          switch (name) {
-            case "toInt":
-              codeGen.wrap(receiver, w.NumType.i64);
-              return w.NumType.i64;
-            case "leU":
-              codeGen.wrap(receiver, w.NumType.i64);
-              codeGen.wrap(node.arguments.positional[0], w.NumType.i64);
-              b.i64_le_u();
-              return boolType;
-            default:
-              throw 'Unknown WasmI64 member $name';
-          }
+          assert(name == "toInt");
+          codeGen.wrap(receiver, w.NumType.i64);
+          return w.NumType.i64;
         case w.NumType.f32:
           assert(name == "toDouble");
           codeGen.wrap(receiver, w.NumType.f32);
           b.f64_promote_f32();
           return w.NumType.f64;
         case w.NumType.f64:
-          switch (name) {
-            case "toDouble":
-              codeGen.wrap(receiver, w.NumType.f64);
-              return w.NumType.f64;
-            case "truncSatS":
-              codeGen.wrap(receiver, w.NumType.f64);
-              b.i64_trunc_sat_f64_s();
-              return w.NumType.i64;
-            default:
-              throw 'Unknown WasmF64 member $name';
-          }
+          assert(name == "toDouble");
+          codeGen.wrap(receiver, w.NumType.f64);
+          return w.NumType.f64;
       }
     }
 
diff --git a/sdk/lib/_internal/wasm/lib/js_helper.dart b/sdk/lib/_internal/wasm/lib/js_helper.dart
index dd5128e..116efcd 100644
--- a/sdk/lib/_internal/wasm/lib/js_helper.dart
+++ b/sdk/lib/_internal/wasm/lib/js_helper.dart
@@ -358,23 +358,23 @@
   } else if (object is String) {
     return jsStringFromDartString(object);
   } else if (object is js_types.JSInt8ArrayImpl) {
-    return object.toJSArrayExternRef();
+    return object.toExternRef;
   } else if (object is js_types.JSUint8ArrayImpl) {
-    return object.toJSArrayExternRef();
+    return object.toExternRef;
   } else if (object is js_types.JSUint8ClampedArrayImpl) {
-    return object.toJSArrayExternRef();
+    return object.toExternRef;
   } else if (object is js_types.JSInt16ArrayImpl) {
-    return object.toJSArrayExternRef();
+    return object.toExternRef;
   } else if (object is js_types.JSUint16ArrayImpl) {
-    return object.toJSArrayExternRef();
+    return object.toExternRef;
   } else if (object is js_types.JSInt32ArrayImpl) {
-    return object.toJSArrayExternRef();
+    return object.toExternRef;
   } else if (object is js_types.JSUint32ArrayImpl) {
-    return object.toJSArrayExternRef();
+    return object.toExternRef;
   } else if (object is js_types.JSFloat32ArrayImpl) {
-    return object.toJSArrayExternRef();
+    return object.toExternRef;
   } else if (object is js_types.JSFloat64ArrayImpl) {
-    return object.toJSArrayExternRef();
+    return object.toExternRef;
   } else if (object is Int8List) {
     return jsInt8ArrayFromDartInt8List(object);
   } else if (object is Uint8List) {
@@ -422,27 +422,27 @@
   } else if (isJSString(ref)) {
     return js_types.JSStringImpl.box(ref);
   } else if (isJSInt8Array(ref)) {
-    return js_types.JSInt8ArrayImpl.fromJSArray(ref);
+    return js_types.JSInt8ArrayImpl(ref);
   } else if (isJSUint8Array(ref)) {
-    return js_types.JSUint8ArrayImpl.fromJSArray(ref);
+    return js_types.JSUint8ArrayImpl(ref);
   } else if (isJSUint8ClampedArray(ref)) {
-    return js_types.JSUint8ClampedArrayImpl.fromJSArray(ref);
+    return js_types.JSUint8ClampedArrayImpl(ref);
   } else if (isJSInt16Array(ref)) {
-    return js_types.JSInt16ArrayImpl.fromJSArray(ref);
+    return js_types.JSInt16ArrayImpl(ref);
   } else if (isJSUint16Array(ref)) {
-    return js_types.JSUint16ArrayImpl.fromJSArray(ref);
+    return js_types.JSUint16ArrayImpl(ref);
   } else if (isJSInt32Array(ref)) {
-    return js_types.JSInt32ArrayImpl.fromJSArray(ref);
+    return js_types.JSInt32ArrayImpl(ref);
   } else if (isJSUint32Array(ref)) {
-    return js_types.JSUint32ArrayImpl.fromJSArray(ref);
+    return js_types.JSUint32ArrayImpl(ref);
   } else if (isJSFloat32Array(ref)) {
-    return js_types.JSFloat32ArrayImpl.fromJSArray(ref);
+    return js_types.JSFloat32ArrayImpl(ref);
   } else if (isJSFloat64Array(ref)) {
-    return js_types.JSFloat64ArrayImpl.fromJSArray(ref);
+    return js_types.JSFloat64ArrayImpl(ref);
   } else if (isJSArrayBuffer(ref)) {
-    return js_types.JSArrayBufferImpl.fromRef(ref);
+    return js_types.JSArrayBufferImpl(ref);
   } else if (isJSDataView(ref)) {
-    return js_types.JSDataViewImpl.fromRef(ref);
+    return js_types.JSDataViewImpl(ref);
   } else if (isJSArray(ref)) {
     return toDartList(ref);
   } else if (isJSWrappedDartFunction(ref)) {
diff --git a/sdk/lib/_internal/wasm/lib/js_interop_patch.dart b/sdk/lib/_internal/wasm/lib/js_interop_patch.dart
index 55a5dfe..2f59ad4 100644
--- a/sdk/lib/_internal/wasm/lib/js_interop_patch.dart
+++ b/sdk/lib/_internal/wasm/lib/js_interop_patch.dart
@@ -136,7 +136,7 @@
 @patch
 extension JSArrayBufferToByteBuffer on JSArrayBuffer {
   @patch
-  ByteBuffer get toDart => js_types.JSArrayBufferImpl.fromRef(toExternRef);
+  ByteBuffer get toDart => js_types.JSArrayBufferImpl(toExternRef);
 }
 
 @patch
@@ -156,7 +156,7 @@
 @patch
 extension JSDataViewToByteData on JSDataView {
   @patch
-  ByteData get toDart => js_types.JSDataViewImpl.fromRef(toExternRef);
+  ByteData get toDart => js_types.JSDataViewImpl(toExternRef);
 }
 
 @patch
@@ -174,7 +174,7 @@
 @patch
 extension JSInt8ArrayToInt8List on JSInt8Array {
   @patch
-  Int8List get toDart => js_types.JSInt8ArrayImpl.fromJSArray(toExternRef);
+  Int8List get toDart => js_types.JSInt8ArrayImpl(toExternRef);
 }
 
 @patch
@@ -192,7 +192,7 @@
 @patch
 extension JSUint8ArrayToUint8List on JSUint8Array {
   @patch
-  Uint8List get toDart => js_types.JSUint8ArrayImpl.fromJSArray(toExternRef);
+  Uint8List get toDart => js_types.JSUint8ArrayImpl(toExternRef);
 }
 
 @patch
@@ -210,8 +210,7 @@
 @patch
 extension JSUint8ClampedArrayToUint8ClampedList on JSUint8ClampedArray {
   @patch
-  Uint8ClampedList get toDart =>
-      js_types.JSUint8ClampedArrayImpl.fromJSArray(toExternRef);
+  Uint8ClampedList get toDart => js_types.JSUint8ClampedArrayImpl(toExternRef);
 }
 
 @patch
@@ -229,7 +228,7 @@
 @patch
 extension JSInt16ArrayToInt16List on JSInt16Array {
   @patch
-  Int16List get toDart => js_types.JSInt16ArrayImpl.fromJSArray(toExternRef);
+  Int16List get toDart => js_types.JSInt16ArrayImpl(toExternRef);
 }
 
 @patch
@@ -247,7 +246,7 @@
 @patch
 extension JSUint16ArrayToInt16List on JSUint16Array {
   @patch
-  Uint16List get toDart => js_types.JSUint16ArrayImpl.fromJSArray(toExternRef);
+  Uint16List get toDart => js_types.JSUint16ArrayImpl(toExternRef);
 }
 
 @patch
@@ -265,7 +264,7 @@
 @patch
 extension JSInt32ArrayToInt32List on JSInt32Array {
   @patch
-  Int32List get toDart => js_types.JSInt32ArrayImpl.fromJSArray(toExternRef);
+  Int32List get toDart => js_types.JSInt32ArrayImpl(toExternRef);
 }
 
 @patch
@@ -283,7 +282,7 @@
 @patch
 extension JSUint32ArrayToUint32List on JSUint32Array {
   @patch
-  Uint32List get toDart => js_types.JSUint32ArrayImpl.fromJSArray(toExternRef);
+  Uint32List get toDart => js_types.JSUint32ArrayImpl(toExternRef);
 }
 
 @patch
@@ -301,8 +300,7 @@
 @patch
 extension JSFloat32ArrayToFloat32List on JSFloat32Array {
   @patch
-  Float32List get toDart =>
-      js_types.JSFloat32ArrayImpl.fromJSArray(toExternRef);
+  Float32List get toDart => js_types.JSFloat32ArrayImpl(toExternRef);
 }
 
 @patch
@@ -320,8 +318,7 @@
 @patch
 extension JSFloat64ArrayToFloat64List on JSFloat64Array {
   @patch
-  Float64List get toDart =>
-      js_types.JSFloat64ArrayImpl.fromJSArray(toExternRef);
+  Float64List get toDart => js_types.JSFloat64ArrayImpl(toExternRef);
 }
 
 @patch
diff --git a/sdk/lib/_internal/wasm/lib/js_string.dart b/sdk/lib/_internal/wasm/lib/js_string.dart
index 47e615b..e500265 100644
--- a/sdk/lib/_internal/wasm/lib/js_string.dart
+++ b/sdk/lib/_internal/wasm/lib/js_string.dart
@@ -314,7 +314,7 @@
   String substring(int start, [int? end]) {
     end = RangeError.checkValidRange(start, end, this.length);
     return JSStringImpl(js.JS<WasmExternRef?>('(o, s, i) => o.substring(s, i)',
-        toExternRef, start.toDouble(), end.toDouble()));
+        toExternRef, start.toDouble().toExternRef, end.toDouble().toExternRef));
   }
 
   @override
diff --git a/sdk/lib/_internal/wasm/lib/js_typed_array.dart b/sdk/lib/_internal/wasm/lib/js_typed_array.dart
index 9f5698f..204d772 100644
--- a/sdk/lib/_internal/wasm/lib/js_typed_array.dart
+++ b/sdk/lib/_internal/wasm/lib/js_typed_array.dart
@@ -4,70 +4,44 @@
 
 part of dart._js_types;
 
-/// A JS `ArrayBuffer`.
 final class JSArrayBufferImpl implements ByteBuffer {
-  /// `externref` of a JS `ArrayBuffer`.
   final WasmExternRef? _ref;
 
-  JSArrayBufferImpl.fromRef(this._ref);
+  JSArrayBufferImpl(this._ref);
 
-  @pragma("wasm:prefer-inline")
   WasmExternRef? get toExternRef => _ref;
 
-  /// Get a JS `DataView` of this `ArrayBuffer`.
-  WasmExternRef? view(int offsetInBytes, int? length) =>
-      _newDataViewFromArrayBuffer(toExternRef, offsetInBytes, length);
-
-  WasmExternRef? cloneAsDataView(int offsetInBytes, int? lengthInBytes) {
-    lengthInBytes ??= this.lengthInBytes;
-    return js.JS<WasmExternRef?>('''(o, offsetInBytes, lengthInBytes) => {
-      var dst = new ArrayBuffer(lengthInBytes);
-      new Uint8Array(dst).set(new Uint8Array(o, offsetInBytes, lengthInBytes));
-      return new DataView(dst);
-    }''', toExternRef, offsetInBytes.toDouble(), lengthInBytes.toDouble());
-  }
-
   @override
-  @pragma("wasm:prefer-inline")
-  int get lengthInBytes => _arrayBufferByteLength(toExternRef);
+  int get lengthInBytes =>
+      js.JS<double>('o => o.byteLength', toExternRef).toInt();
 
-  @override
   Uint8List asUint8List([int offsetInBytes = 0, int? length]) =>
       JSUint8ArrayImpl.view(this, offsetInBytes, length);
 
-  @override
   Int8List asInt8List([int offsetInBytes = 0, int? length]) =>
       JSInt8ArrayImpl.view(this, offsetInBytes, length);
 
-  @override
   Uint8ClampedList asUint8ClampedList([int offsetInBytes = 0, int? length]) =>
       JSUint8ClampedArrayImpl.view(this, offsetInBytes, length);
 
-  @override
   Uint16List asUint16List([int offsetInBytes = 0, int? length]) =>
       JSUint16ArrayImpl.view(this, offsetInBytes, length);
 
-  @override
   Int16List asInt16List([int offsetInBytes = 0, int? length]) =>
       JSInt16ArrayImpl.view(this, offsetInBytes, length);
 
-  @override
   Uint32List asUint32List([int offsetInBytes = 0, int? length]) =>
       JSUint32ArrayImpl.view(this, offsetInBytes, length);
 
-  @override
   Int32List asInt32List([int offsetInBytes = 0, int? length]) =>
       JSInt32ArrayImpl.view(this, offsetInBytes, length);
 
-  @override
   Uint64List asUint64List([int offsetInBytes = 0, int? length]) =>
       JSBigUint64ArrayImpl.view(this, offsetInBytes, length);
 
-  @override
   Int64List asInt64List([int offsetInBytes = 0, int? length]) =>
       JSBigInt64ArrayImpl.view(this, offsetInBytes, length);
 
-  @override
   Int32x4List asInt32x4List([int offsetInBytes = 0, int? length]) {
     _offsetAlignmentCheck(offsetInBytes, Int32x4List.bytesPerElement);
     length ??= (lengthInBytes - offsetInBytes) ~/ Int32x4List.bytesPerElement;
@@ -75,15 +49,12 @@
     return JSInt32x4ArrayImpl.externalStorage(storage);
   }
 
-  @override
   Float32List asFloat32List([int offsetInBytes = 0, int? length]) =>
       JSFloat32ArrayImpl.view(this, offsetInBytes, length);
 
-  @override
   Float64List asFloat64List([int offsetInBytes = 0, int? length]) =>
       JSFloat64ArrayImpl.view(this, offsetInBytes, length);
 
-  @override
   Float32x4List asFloat32x4List([int offsetInBytes = 0, int? length]) {
     _offsetAlignmentCheck(offsetInBytes, Float32x4List.bytesPerElement);
     length ??= (lengthInBytes - offsetInBytes) ~/ Float32x4List.bytesPerElement;
@@ -91,7 +62,6 @@
     return JSFloat32x4ArrayImpl.externalStorage(storage);
   }
 
-  @override
   Float64x2List asFloat64x2List([int offsetInBytes = 0, int? length]) {
     _offsetAlignmentCheck(offsetInBytes, Float64x2List.bytesPerElement);
     length ??= (lengthInBytes - offsetInBytes) ~/ Float64x2List.bytesPerElement;
@@ -99,165 +69,187 @@
     return JSFloat64x2ArrayImpl.externalStorage(storage);
   }
 
-  @override
   ByteData asByteData([int offsetInBytes = 0, int? length]) =>
       JSDataViewImpl.view(this, offsetInBytes, length);
 
   @override
   bool operator ==(Object that) =>
       that is JSArrayBufferImpl && js.areEqualInJS(_ref, that._ref);
+
+  @override
+  int get hashCode => 0;
 }
 
-/// Base class for all JS typed array classes.
-abstract class JSArrayBase implements TypedData {
-  /// `externref` of a JS `DataView`.
+final class JSArrayBufferViewImpl implements TypedData {
   final WasmExternRef? _ref;
 
-  JSArrayBase(this._ref);
+  JSArrayBufferViewImpl(this._ref);
 
-  @pragma("wasm:prefer-inline")
   WasmExternRef? get toExternRef => _ref;
 
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]);
+  @override
+  ByteBuffer get buffer =>
+      JSArrayBufferImpl(js.JS<WasmExternRef?>('o => o.buffer', toExternRef));
 
   @override
-  JSArrayBufferImpl get buffer =>
-      JSArrayBufferImpl.fromRef(_dataViewBuffer(_ref));
+  int get lengthInBytes =>
+      js.JS<double>('o => o.byteLength', toExternRef).toInt();
 
   @override
-  @pragma("wasm:prefer-inline")
-  int get lengthInBytes => _dataViewByteLength(toExternRef);
+  int get offsetInBytes =>
+      js.JS<double>('o => o.byteOffset', toExternRef).toInt();
 
   @override
-  @pragma("wasm:prefer-inline")
-  int get offsetInBytes => _dataViewByteOffset(_ref);
+  int get elementSizeInBytes =>
+      js.JS<double>('o => o.BYTES_PER_ELEMENT', toExternRef).toInt();
+
+  int get length => js.JS<double>('o => o.length', toExternRef).toInt();
 
   @override
   bool operator ==(Object that) =>
-      that is JSArrayBase && js.areEqualInJS(_ref, that._ref);
+      that is JSArrayBufferViewImpl && js.areEqualInJS(_ref, that._ref);
+
+  @override
+  int get hashCode => 0;
 }
 
-/// A JS `DataView`.
-final class JSDataViewImpl implements ByteData {
-  /// `externref` of a JS `DataView`.
-  final WasmExternRef? _ref;
-
-  JSDataViewImpl(int length) : _ref = _newDataView(length);
-
-  JSDataViewImpl.fromRef(this._ref);
+final class JSDataViewImpl extends JSArrayBufferViewImpl implements ByteData {
+  JSDataViewImpl(super._ref);
 
   factory JSDataViewImpl.view(
-          JSArrayBufferImpl buffer, int offsetInBytes, int? length) =>
-      JSDataViewImpl.fromRef(_newDataViewFromArrayBuffer(
-          buffer.toExternRef, offsetInBytes, length));
-
-  @pragma("wasm:prefer-inline")
-  WasmExternRef? get toExternRef => _ref;
+      JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
+    WasmExternRef? jsBuffer;
+    if (length == null) {
+      jsBuffer = js.JS<WasmExternRef?>('(b, o) => new DataView(b, o)',
+          buffer.toExternRef, offsetInBytes.toDouble());
+    } else {
+      jsBuffer = js.JS<WasmExternRef?>('(b, o, l) => new DataView(b, o, l)',
+          buffer.toExternRef, offsetInBytes.toDouble(), length.toDouble());
+    }
+    return JSDataViewImpl(jsBuffer);
+  }
 
   @override
-  JSArrayBufferImpl get buffer =>
-      JSArrayBufferImpl.fromRef(_dataViewBuffer(toExternRef));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get lengthInBytes => _dataViewByteLength(toExternRef);
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get offsetInBytes => _dataViewByteOffset(_ref);
-
-  @override
-  @pragma("wasm:prefer-inline")
   int get elementSizeInBytes => 1;
 
   @override
   ByteData asUnmodifiableView() => UnmodifiableByteDataView(this);
 
-  @override
   double getFloat32(int byteOffset, [Endian endian = Endian.big]) =>
-      _getFloat32(toExternRef, byteOffset, Endian.little == endian);
+      js.JS<double>('(b, o, e) => b.getFloat32(o, e)', toExternRef,
+          byteOffset.toDouble(), Endian.little == endian);
 
-  @override
   double getFloat64(int byteOffset, [Endian endian = Endian.big]) =>
-      _getFloat64(toExternRef, byteOffset, Endian.little == endian);
+      js.JS<double>('(b, o, e) => b.getFloat64(o, e)', toExternRef,
+          byteOffset.toDouble(), Endian.little == endian);
 
-  @override
-  int getInt16(int byteOffset, [Endian endian = Endian.big]) =>
-      _getInt16(toExternRef, byteOffset, Endian.little == endian);
+  int getInt16(int byteOffset, [Endian endian = Endian.big]) => js
+      .JS<double>('(b, o, e) => b.getInt16(o, e)', toExternRef,
+          byteOffset.toDouble(), Endian.little == endian)
+      .toInt();
 
-  @override
-  int getInt32(int byteOffset, [Endian endian = Endian.big]) =>
-      _getInt32(toExternRef, byteOffset, Endian.little == endian);
+  int getInt32(int byteOffset, [Endian endian = Endian.big]) => js
+      .JS<double>('(b, o, e) => b.getInt32(o, e)', toExternRef,
+          byteOffset.toDouble(), Endian.little == endian)
+      .toInt();
 
-  @override
-  int getInt64(int byteOffset, [Endian endian = Endian.big]) =>
-      _getBigInt64(toExternRef, byteOffset, Endian.little == endian);
+  int getInt64(int byteOffset, [Endian endian = Endian.big]) => js.JS<int>(
+      '(b, o, e) => b.getBigInt64(o, e)',
+      toExternRef,
+      byteOffset.toDouble(),
+      Endian.little == endian);
 
-  @override
-  int getInt8(int byteOffset) => _getInt8(toExternRef, byteOffset);
+  int getInt8(int byteOffset) => js
+      .JS<double>('(b, o) => b.getInt8(o)', toExternRef, byteOffset.toDouble())
+      .toInt();
 
-  @override
-  int getUint16(int byteOffset, [Endian endian = Endian.big]) =>
-      _getUint16(toExternRef, byteOffset, Endian.little == endian);
+  int getUint16(int byteOffset, [Endian endian = Endian.big]) => js
+      .JS<double>('(b, o, e) => b.getUint16(o, e)', toExternRef,
+          byteOffset.toDouble(), Endian.little == endian)
+      .toInt();
 
-  @override
-  int getUint32(int byteOffset, [Endian endian = Endian.big]) =>
-      _getUint32(toExternRef, byteOffset, Endian.little == endian);
+  int getUint32(int byteOffset, [Endian endian = Endian.big]) => js
+      .JS<double>('(b, o, e) => b.getUint32(o, e)', toExternRef,
+          byteOffset.toDouble(), Endian.little == endian)
+      .toInt();
 
-  @override
-  int getUint64(int byteOffset, [Endian endian = Endian.big]) =>
-      _getBigUint64(toExternRef, byteOffset, Endian.little == endian);
+  int getUint64(int byteOffset, [Endian endian = Endian.big]) => js.JS<int>(
+      '(b, o, e) => b.getBigUint64(o, e)',
+      toExternRef,
+      byteOffset.toDouble(),
+      Endian.little == endian);
 
-  @override
-  int getUint8(int byteOffset) => _getUint8(toExternRef, byteOffset);
+  int getUint8(int byteOffset) => js
+      .JS<double>('(b, o) => b.getUint8(o)', toExternRef, byteOffset.toDouble())
+      .toInt();
 
-  @override
   void setFloat32(int byteOffset, num value, [Endian endian = Endian.big]) =>
-      _setFloat32(toExternRef, byteOffset, value, Endian.little == endian);
+      js.JS<void>('(b, o, v, e) => b.setFloat32(o, v, e)', toExternRef,
+          byteOffset.toDouble(), value.toDouble(), Endian.little == endian);
 
-  @override
   void setFloat64(int byteOffset, num value, [Endian endian = Endian.big]) =>
-      _setFloat64(toExternRef, byteOffset, value, Endian.little == endian);
+      js.JS<void>('(b, o, v, e) => b.setFloat64(o, v, e)', toExternRef,
+          byteOffset.toDouble(), value.toDouble(), Endian.little == endian);
 
-  @override
   void setInt16(int byteOffset, int value, [Endian endian = Endian.big]) =>
-      _setInt16(toExternRef, byteOffset, value, Endian.little == endian);
+      js.JS<void>('(b, o, v, e) => b.setInt16(o, v, e)', toExternRef,
+          byteOffset.toDouble(), value.toDouble(), Endian.little == endian);
 
-  @override
   void setInt32(int byteOffset, int value, [Endian endian = Endian.big]) =>
-      _setInt32(toExternRef, byteOffset, value, Endian.little == endian);
+      js.JS<void>('(b, o, v, e) => b.setInt32(o, v, e)', toExternRef,
+          byteOffset.toDouble(), value.toDouble(), Endian.little == endian);
 
-  @override
   void setInt64(int byteOffset, int value, [Endian endian = Endian.big]) =>
-      _setBigInt64(toExternRef, byteOffset, value, Endian.little == endian);
+      js.JS<void>('(b, o, v, e) => b.setBigInt64(o, v, e)', toExternRef,
+          byteOffset.toDouble(), value, Endian.little == endian);
 
-  @override
-  void setInt8(int byteOffset, int value) =>
-      _setInt8(toExternRef, byteOffset, value);
+  void setInt8(int byteOffset, int value) => js.JS<void>(
+      '(b, o, v) => b.setInt8(o, v)',
+      toExternRef,
+      byteOffset.toDouble(),
+      value.toDouble());
 
-  @override
   void setUint16(int byteOffset, int value, [Endian endian = Endian.big]) =>
-      _setUint16(toExternRef, byteOffset, value, Endian.little == endian);
+      js.JS<void>('(b, o, v, e) => b.setUint16(o, v, e)', toExternRef,
+          byteOffset.toDouble(), value.toDouble(), Endian.little == endian);
 
-  @override
   void setUint32(int byteOffset, int value, [Endian endian = Endian.big]) =>
-      _setUint32(toExternRef, byteOffset, value, Endian.little == endian);
+      js.JS<void>('(b, o, v, e) => b.setUint32(o, v, e)', toExternRef,
+          byteOffset.toDouble(), value.toDouble(), Endian.little == endian);
 
-  @override
   void setUint64(int byteOffset, int value, [Endian endian = Endian.big]) =>
-      _setBigUint64(toExternRef, byteOffset, value, Endian.little == endian);
+      js.JS<void>('(b, o, v, e) => b.setBigUint64(o, v, e)', toExternRef,
+          byteOffset.toDouble(), value, Endian.little == endian);
 
-  @override
-  void setUint8(int byteOffset, int value) =>
-      _setUint8(toExternRef, byteOffset, value);
+  void setUint8(int byteOffset, int value) => js.JS<void>(
+      '(b, o, v) => b.setUint8(o, v)',
+      toExternRef,
+      byteOffset.toDouble(),
+      value.toDouble());
 }
 
-/// Base class for `int` typed lists.
-abstract class JSIntArrayImpl extends JSArrayBase
+final class JSIntArrayImpl extends JSArrayBufferViewImpl
     with ListMixin<int>, FixedLengthListMixin<int> {
   JSIntArrayImpl(super._ref);
 
   @override
+  @pragma("wasm:prefer-inline")
+  int operator [](int index) {
+    IndexError.check(index, length);
+    return js
+        .JS<double>('(o, i) => o[i]', toExternRef, index.toDouble())
+        .toInt();
+  }
+
+  @override
+  @pragma("wasm:prefer-inline")
+  void operator []=(int index, int value) {
+    IndexError.check(index, length);
+    js.JS<void>('(o, i, v) => o[i] = v', toExternRef, index.toDouble(),
+        value.toDouble());
+  }
+
+  @override
   void setAll(int index, Iterable<int> iterable) {
     final end = iterable.length + index;
     setRange(index, end, iterable);
@@ -266,75 +258,48 @@
   @override
   void setRange(int start, int end, Iterable<int> iterable,
       [int skipCount = 0]) {
+    int count = end - start;
     RangeError.checkValidRange(start, end, length);
 
-    if (skipCount < 0) {
-      throw ArgumentError(skipCount);
-    }
+    if (skipCount < 0) throw ArgumentError(skipCount);
 
-    if (iterable is JSArrayBase) {
-      final JSArrayBase source = unsafeCast<JSArrayBase>(iterable);
-      final length = end - start;
-      final sourceArray = source.toJSArrayExternRef(skipCount, length);
-      final targetArray = toJSArrayExternRef(start, length);
-      return _setRangeFast(targetArray, sourceArray);
-    }
-
-    List<int> otherList = iterable.skip(skipCount).toList(growable: false);
-
-    int count = end - start;
-    if (otherList.length < count) {
+    int sourceLength = iterable.length;
+    if (sourceLength - skipCount < count) {
       throw IterableElementError.tooFew();
     }
 
-    // TODO(omersa): Use unchecked operations here.
-    for (int i = 0, j = start; i < count; i++, j++) {
-      this[j] = otherList[i];
+    if (iterable is JSArrayBufferViewImpl) {
+      _setRangeFast(this, start, end, count, iterable as JSArrayBufferViewImpl,
+          sourceLength, skipCount);
+    } else {
+      List<int> otherList;
+      int otherStart;
+      if (iterable is List<int>) {
+        otherList = iterable;
+        otherStart = skipCount;
+      } else {
+        otherList = iterable.skip(skipCount).toList(growable: false);
+        otherStart = 0;
+      }
+      Lists.copy(otherList, otherStart, this, start, count);
     }
   }
 }
 
 final class JSUint8ArrayImpl extends JSIntArrayImpl implements Uint8List {
-  JSUint8ArrayImpl._(super._ref);
-
-  factory JSUint8ArrayImpl(int length) =>
-      JSUint8ArrayImpl._(_newDataView(length));
-
-  factory JSUint8ArrayImpl.fromJSArray(WasmExternRef? jsArrayRef) =>
-      JSUint8ArrayImpl._(_dataViewFromJSArray(jsArrayRef));
+  JSUint8ArrayImpl(super._ref);
 
   factory JSUint8ArrayImpl.view(
-          JSArrayBufferImpl buffer, int offsetInBytes, int? length) =>
-      JSUint8ArrayImpl._(buffer.view(offsetInBytes, length));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get elementSizeInBytes => 1;
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get length => lengthInBytes;
-
-  @override
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]) => js.JS<
-          WasmExternRef?>(
-      '(o, start, length) => new Uint8Array(o.buffer, o.byteOffset + start, length)',
-      toExternRef,
-      WasmI32.fromInt(start),
-      WasmI32.fromInt(length ?? (this.length - start)));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int operator [](int index) {
-    _indexCheck(index, length);
-    return _getUint8(toExternRef, index);
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  void operator []=(int index, int value) {
-    _indexCheck(index, length);
-    _setUint8(toExternRef, index, value);
+      JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
+    WasmExternRef? jsBuffer;
+    if (length == null) {
+      jsBuffer = js.JS<WasmExternRef?>('(b, o) => new Uint8Array(b, o)',
+          buffer.toExternRef, offsetInBytes.toDouble());
+    } else {
+      jsBuffer = js.JS<WasmExternRef?>('(b, o, l) => new Uint8Array(b, o, l)',
+          buffer.toExternRef, offsetInBytes.toDouble(), length.toDouble());
+    }
+    return JSUint8ArrayImpl(jsBuffer);
   }
 
   @override
@@ -342,54 +307,30 @@
 
   @override
   Uint8List sublist(int start, [int? end]) {
-    final newOffset = offsetInBytes + start;
-    final newEnd = RangeError.checkValidRange(newOffset, end, lengthInBytes);
-    final newLength = newEnd - newOffset;
-    return JSUint8ArrayImpl._(buffer.cloneAsDataView(newOffset, newLength));
+    final stop = RangeError.checkValidRange(start, end, length);
+    final source = js.JS<WasmExternRef?>(
+        '(a, s, p) => new Uint8Array(a.subarray(s, p))',
+        toExternRef,
+        start.toDouble(),
+        stop.toDouble());
+    return JSUint8ArrayImpl(source);
   }
 }
 
 final class JSInt8ArrayImpl extends JSIntArrayImpl implements Int8List {
-  JSInt8ArrayImpl._(super._ref);
-
-  factory JSInt8ArrayImpl(int length) =>
-      JSInt8ArrayImpl._(_newDataView(length));
-
-  factory JSInt8ArrayImpl.fromJSArray(WasmExternRef? jsArrayRef) =>
-      JSInt8ArrayImpl._(_dataViewFromJSArray(jsArrayRef));
+  JSInt8ArrayImpl(super._ref);
 
   factory JSInt8ArrayImpl.view(
-          JSArrayBufferImpl buffer, int offsetInBytes, int? length) =>
-      JSInt8ArrayImpl._(buffer.view(offsetInBytes, length));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get elementSizeInBytes => 1;
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get length => lengthInBytes;
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int operator [](int index) {
-    _indexCheck(index, length);
-    return _getInt8(toExternRef, index);
-  }
-
-  @override
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]) => js.JS<
-          WasmExternRef?>(
-      '(o, start, length) => new Int8Array(o.buffer, o.byteOffset + start, length)',
-      toExternRef,
-      WasmI32.fromInt(start),
-      WasmI32.fromInt(length ?? (this.length - start)));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  void operator []=(int index, int value) {
-    _indexCheck(index, length);
-    _setInt8(toExternRef, index, value);
+      JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
+    WasmExternRef? jsBuffer;
+    if (length == null) {
+      jsBuffer = js.JS<WasmExternRef?>('(b, o) => new Int8Array(b, o)',
+          buffer.toExternRef, offsetInBytes.toDouble());
+    } else {
+      jsBuffer = js.JS<WasmExternRef?>('(b, o, l) => new Int8Array(b, o, l)',
+          buffer.toExternRef, offsetInBytes.toDouble(), length.toDouble());
+    }
+    return JSInt8ArrayImpl(jsBuffer);
   }
 
   @override
@@ -397,55 +338,34 @@
 
   @override
   Int8List sublist(int start, [int? end]) {
-    final newOffset = offsetInBytes + start;
-    final newEnd = RangeError.checkValidRange(newOffset, end, lengthInBytes);
-    final newLength = newEnd - newOffset;
-    return JSInt8ArrayImpl._(buffer.cloneAsDataView(newOffset, newLength));
+    final stop = RangeError.checkValidRange(start, end, length);
+    final source = js.JS<WasmExternRef?>(
+        '(a, s, p) => new Int8Array(a.subarray(s, p))',
+        toExternRef,
+        start.toDouble(),
+        stop.toDouble());
+    return JSInt8ArrayImpl(source);
   }
 }
 
 final class JSUint8ClampedArrayImpl extends JSIntArrayImpl
     implements Uint8ClampedList {
-  JSUint8ClampedArrayImpl._(super._ref);
-
-  factory JSUint8ClampedArrayImpl(int length) =>
-      JSUint8ClampedArrayImpl._(_newDataView(length));
-
-  factory JSUint8ClampedArrayImpl.fromJSArray(WasmExternRef? jsArrayRef) =>
-      JSUint8ClampedArrayImpl._(_dataViewFromJSArray(jsArrayRef));
+  JSUint8ClampedArrayImpl(super._ref);
 
   factory JSUint8ClampedArrayImpl.view(
-          JSArrayBufferImpl buffer, int offsetInBytes, int? length) =>
-      JSUint8ClampedArrayImpl._(buffer.view(offsetInBytes, length));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get elementSizeInBytes => 1;
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get length => lengthInBytes;
-
-  @override
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]) => js.JS<
-          WasmExternRef?>(
-      '(o, start, length) => new Uint8ClampedArray(o.buffer, o.byteOffset + start, length)',
-      toExternRef,
-      WasmI32.fromInt(start),
-      WasmI32.fromInt(length ?? (this.length - start)));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int operator [](int index) {
-    _indexCheck(index, length);
-    return _getUint8(toExternRef, index);
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  void operator []=(int index, int value) {
-    _indexCheck(index, length);
-    _setUint8(toExternRef, index, value.clamp(0, 255));
+      JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
+    WasmExternRef? jsBuffer;
+    if (length == null) {
+      jsBuffer = js.JS<WasmExternRef?>('(b, o) => new Uint8ClampedArray(b, o)',
+          buffer.toExternRef, offsetInBytes.toDouble());
+    } else {
+      jsBuffer = js.JS<WasmExternRef?>(
+          '(b, o, l) => new Uint8ClampedArray(b, o, l)',
+          buffer.toExternRef,
+          offsetInBytes.toDouble(),
+          length.toDouble());
+    }
+    return JSUint8ClampedArrayImpl(jsBuffer);
   }
 
   @override
@@ -454,60 +374,29 @@
 
   @override
   Uint8ClampedList sublist(int start, [int? end]) {
-    final newOffset = offsetInBytes + start;
-    final newEnd = RangeError.checkValidRange(newOffset, end, lengthInBytes);
-    final newLength = newEnd - newOffset;
-    return JSUint8ClampedArrayImpl._(
-        buffer.cloneAsDataView(newOffset, newLength));
+    final stop = RangeError.checkValidRange(start, end, length);
+    final source = js.JS<WasmExternRef?>(
+        '(a, s, p) => new Uint8ClampedArray(a.subarray(s, p))',
+        toExternRef,
+        start.toDouble(),
+        stop.toDouble());
+    return JSUint8ClampedArrayImpl(source);
   }
 }
 
 final class JSUint16ArrayImpl extends JSIntArrayImpl implements Uint16List {
-  JSUint16ArrayImpl._(super._ref);
-
-  factory JSUint16ArrayImpl(int length) =>
-      JSUint16ArrayImpl._(_newDataView(length * 2));
-
-  factory JSUint16ArrayImpl.fromJSArray(WasmExternRef? jsArrayRef) =>
-      JSUint16ArrayImpl._(_dataViewFromJSArray(jsArrayRef));
+  JSUint16ArrayImpl(super._ref);
 
   factory JSUint16ArrayImpl.view(
       JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
     _offsetAlignmentCheck(offsetInBytes, Uint16List.bytesPerElement);
-    final lengthInBytes = (length == null
-        ? ((buffer.lengthInBytes - offsetInBytes) & -2)
-        : length * 2);
-    return JSUint16ArrayImpl._(buffer.view(offsetInBytes, lengthInBytes));
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get elementSizeInBytes => 2;
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get length => lengthInBytes >>> 1;
-
-  @override
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]) => js.JS<
-          WasmExternRef?>(
-      '(o, start, length) => new Uint16Array(o.buffer, o.byteOffset + start, length)',
-      toExternRef,
-      WasmI32.fromInt(start * 2),
-      WasmI32.fromInt(length ?? (this.length - start)));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int operator [](int index) {
-    _indexCheck(index, length);
-    return _getUint16(toExternRef, index * 2, true);
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  void operator []=(int index, int value) {
-    _indexCheck(index, length);
-    _setUint16(toExternRef, index * 2, value, true);
+    length ??= _adjustLength(buffer, offsetInBytes, Uint16List.bytesPerElement);
+    WasmExternRef? jsBuffer = js.JS<WasmExternRef?>(
+        '(b, o, l) => new Uint16Array(b, o, l)',
+        buffer.toExternRef,
+        offsetInBytes.toDouble(),
+        length.toDouble());
+    return JSUint16ArrayImpl(jsBuffer);
   }
 
   @override
@@ -515,60 +404,29 @@
 
   @override
   Uint16List sublist(int start, [int? end]) {
-    final int newOffset = offsetInBytes + (start * 2);
-    final int newEnd = end == null ? lengthInBytes : end * 2;
-    final int newLength = newEnd - newOffset;
-    RangeError.checkValidRange(newOffset ~/ 2, newEnd ~/ 2, lengthInBytes ~/ 2);
-    return JSUint16ArrayImpl._(buffer.cloneAsDataView(newOffset, newLength));
+    final stop = RangeError.checkValidRange(start, end, length);
+    final source = js.JS<WasmExternRef?>(
+        '(a, s, p) => new Uint16Array(a.subarray(s, p))',
+        toExternRef,
+        start.toDouble(),
+        stop.toDouble());
+    return JSUint16ArrayImpl(source);
   }
 }
 
 final class JSInt16ArrayImpl extends JSIntArrayImpl implements Int16List {
-  JSInt16ArrayImpl._(super._ref);
-
-  factory JSInt16ArrayImpl(int length) =>
-      JSInt16ArrayImpl._(_newDataView(length * 2));
-
-  factory JSInt16ArrayImpl.fromJSArray(WasmExternRef? jsArrayRef) =>
-      JSInt16ArrayImpl._(_dataViewFromJSArray(jsArrayRef));
+  JSInt16ArrayImpl(super._ref);
 
   factory JSInt16ArrayImpl.view(
       JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
     _offsetAlignmentCheck(offsetInBytes, Int16List.bytesPerElement);
-    final lengthInBytes = (length == null
-        ? ((buffer.lengthInBytes - offsetInBytes) & -2)
-        : length * 2);
-    return JSInt16ArrayImpl._(buffer.view(offsetInBytes, lengthInBytes));
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get elementSizeInBytes => 2;
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get length => lengthInBytes >>> 1;
-
-  @override
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]) => js.JS<
-          WasmExternRef?>(
-      '(o, start, length) => new Int16Array(o.buffer, o.byteOffset + start, length)',
-      toExternRef,
-      WasmI32.fromInt(start * 2),
-      WasmI32.fromInt(length ?? (this.length - start)));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int operator [](int index) {
-    _indexCheck(index, length);
-    return _getInt16(toExternRef, index * 2, true);
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  void operator []=(int index, int value) {
-    _indexCheck(index, length);
-    _setInt16(toExternRef, index * 2, value, true);
+    length ??= _adjustLength(buffer, offsetInBytes, Int16List.bytesPerElement);
+    WasmExternRef? jsBuffer = js.JS<WasmExternRef?>(
+        '(b, o, l) => new Int16Array(b, o, l)',
+        buffer.toExternRef,
+        offsetInBytes.toDouble(),
+        length.toDouble());
+    return JSInt16ArrayImpl(jsBuffer);
   }
 
   @override
@@ -576,60 +434,29 @@
 
   @override
   Int16List sublist(int start, [int? end]) {
-    final int newOffset = offsetInBytes + (start * 2);
-    final int newEnd = end == null ? lengthInBytes : end * 2;
-    final int newLength = newEnd - newOffset;
-    RangeError.checkValidRange(newOffset ~/ 2, newEnd ~/ 2, lengthInBytes ~/ 2);
-    return JSInt16ArrayImpl._(buffer.cloneAsDataView(newOffset, newLength));
+    final stop = RangeError.checkValidRange(start, end, length);
+    final source = js.JS<WasmExternRef?>(
+        '(a, s, p) => new Int16Array(a.subarray(s, p))',
+        toExternRef,
+        start.toDouble(),
+        stop.toDouble());
+    return JSInt16ArrayImpl(source);
   }
 }
 
 final class JSUint32ArrayImpl extends JSIntArrayImpl implements Uint32List {
-  JSUint32ArrayImpl._(super._ref);
-
-  factory JSUint32ArrayImpl(int length) =>
-      JSUint32ArrayImpl._(_newDataView(length * 4));
-
-  factory JSUint32ArrayImpl.fromJSArray(WasmExternRef? jsArrayRef) =>
-      JSUint32ArrayImpl._(_dataViewFromJSArray(jsArrayRef));
+  JSUint32ArrayImpl(super._ref);
 
   factory JSUint32ArrayImpl.view(
       JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
     _offsetAlignmentCheck(offsetInBytes, Uint32List.bytesPerElement);
-    final lengthInBytes = (length == null
-        ? ((buffer.lengthInBytes - offsetInBytes) & -4)
-        : length * 4);
-    return JSUint32ArrayImpl._(buffer.view(offsetInBytes, lengthInBytes));
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get elementSizeInBytes => 4;
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get length => lengthInBytes >>> 2;
-
-  @override
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]) => js.JS<
-          WasmExternRef?>(
-      '(o, start, length) => new Uint32Array(o.buffer, o.byteOffset + start, length)',
-      toExternRef,
-      WasmI32.fromInt(start * 4),
-      WasmI32.fromInt(length ?? (this.length - start)));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int operator [](int index) {
-    _indexCheck(index, length);
-    return _getUint32(toExternRef, index * 4, true);
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  void operator []=(int index, int value) {
-    _indexCheck(index, length);
-    _setUint32(toExternRef, index * 4, value, true);
+    length ??= _adjustLength(buffer, offsetInBytes, Uint32List.bytesPerElement);
+    WasmExternRef? jsBuffer = js.JS<WasmExternRef?>(
+        '(b, o, l) => new Uint32Array(b, o, l)',
+        buffer.toExternRef,
+        offsetInBytes.toDouble(),
+        length.toDouble());
+    return JSUint32ArrayImpl(jsBuffer);
   }
 
   @override
@@ -637,60 +464,29 @@
 
   @override
   Uint32List sublist(int start, [int? end]) {
-    final int newOffset = offsetInBytes + (start * 4);
-    final int newEnd = end == null ? lengthInBytes : end * 4;
-    final int newLength = newEnd - newOffset;
-    RangeError.checkValidRange(newOffset ~/ 4, newEnd ~/ 4, lengthInBytes ~/ 4);
-    return JSUint32ArrayImpl._(buffer.cloneAsDataView(newOffset, newLength));
+    final stop = RangeError.checkValidRange(start, end, length);
+    final source = js.JS<WasmExternRef?>(
+        '(a, s, p) => new Uint32Array(a.subarray(s, p))',
+        toExternRef,
+        start.toDouble(),
+        stop.toDouble());
+    return JSUint32ArrayImpl(source);
   }
 }
 
 final class JSInt32ArrayImpl extends JSIntArrayImpl implements Int32List {
-  JSInt32ArrayImpl._(super._ref);
-
-  factory JSInt32ArrayImpl(int length) =>
-      JSInt32ArrayImpl._(_newDataView(length * 4));
-
-  factory JSInt32ArrayImpl.fromJSArray(WasmExternRef? jsArrayRef) =>
-      JSInt32ArrayImpl._(_dataViewFromJSArray(jsArrayRef));
+  JSInt32ArrayImpl(super._ref);
 
   factory JSInt32ArrayImpl.view(
       JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
     _offsetAlignmentCheck(offsetInBytes, Int32List.bytesPerElement);
-    final lengthInBytes = (length == null
-        ? ((buffer.lengthInBytes - offsetInBytes) & -4)
-        : length * 4);
-    return JSInt32ArrayImpl._(buffer.view(offsetInBytes, lengthInBytes));
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get length => lengthInBytes >>> 2;
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get elementSizeInBytes => 4;
-
-  @override
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]) => js.JS<
-          WasmExternRef?>(
-      '(o, start, length) => new Int32Array(o.buffer, o.byteOffset + start, length)',
-      toExternRef,
-      WasmI32.fromInt(start * 4),
-      WasmI32.fromInt(length ?? (this.length - start)));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int operator [](int index) {
-    _indexCheck(index, length);
-    return _getInt32(toExternRef, index * 4, true);
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  void operator []=(int index, int value) {
-    _indexCheck(index, length);
-    _setInt32(toExternRef, index * 4, value, true);
+    length ??= _adjustLength(buffer, offsetInBytes, Int32List.bytesPerElement);
+    WasmExternRef? jsBuffer = js.JS<WasmExternRef?>(
+        '(b, o, l) => new Int32Array(b, o, l)',
+        buffer.toExternRef,
+        offsetInBytes.toDouble(),
+        length.toDouble());
+    return JSInt32ArrayImpl(jsBuffer);
   }
 
   @override
@@ -698,11 +494,13 @@
 
   @override
   Int32List sublist(int start, [int? end]) {
-    final int newOffset = offsetInBytes + (start * 4);
-    final int newEnd = end == null ? lengthInBytes : end * 4;
-    final int newLength = newEnd - newOffset;
-    RangeError.checkValidRange(newOffset ~/ 4, newEnd ~/ 4, lengthInBytes ~/ 4);
-    return JSInt32ArrayImpl._(buffer.cloneAsDataView(newOffset, newLength));
+    final stop = RangeError.checkValidRange(start, end, length);
+    final source = js.JS<WasmExternRef?>(
+        '(a, s, p) => new Int32Array(a.subarray(s, p))',
+        toExternRef,
+        start.toDouble(),
+        stop.toDouble());
+    return JSInt32ArrayImpl(source);
   }
 }
 
@@ -718,7 +516,6 @@
   ByteBuffer get buffer => _storage.buffer;
 
   @override
-  @pragma("wasm:prefer-inline")
   int get lengthInBytes => _storage.lengthInBytes;
 
   @override
@@ -728,13 +525,12 @@
   int get elementSizeInBytes => Int32x4List.bytesPerElement;
 
   @override
-  @pragma("wasm:prefer-inline")
   int get length => _storage.length ~/ 4;
 
   @override
   @pragma("wasm:prefer-inline")
   Int32x4 operator [](int index) {
-    _indexCheck(index, length);
+    IndexError.check(index, length);
     int _x = _storage[(index * 4) + 0];
     int _y = _storage[(index * 4) + 1];
     int _z = _storage[(index * 4) + 2];
@@ -745,7 +541,7 @@
   @override
   @pragma("wasm:prefer-inline")
   void operator []=(int index, Int32x4 value) {
-    _indexCheck(index, length);
+    IndexError.check(index, length);
     _storage[(index * 4) + 0] = value.x;
     _storage[(index * 4) + 1] = value.y;
     _storage[(index * 4) + 2] = value.z;
@@ -761,87 +557,40 @@
     return JSInt32x4ArrayImpl.externalStorage(
         _storage.sublist(start * 4, stop * 4) as JSInt32ArrayImpl);
   }
-
-  @override
-  void setAll(int index, Iterable<Int32x4> iterable) {
-    final end = iterable.length + index;
-    setRange(index, end, iterable);
-  }
-
-  @override
-  void setRange(int start, int end, Iterable<Int32x4> iterable,
-      [int skipCount = 0]) {
-    RangeError.checkValidRange(start, end, length);
-
-    if (skipCount < 0) {
-      throw ArgumentError(skipCount);
-    }
-
-    List<Int32x4> otherList = iterable.skip(skipCount).toList(growable: false);
-
-    int count = end - start;
-    if (otherList.length < count) {
-      throw IterableElementError.tooFew();
-    }
-
-    // TODO(omersa): Use unchecked operations here.
-    for (int i = 0, j = start; i < count; i++, j++) {
-      this[j] = otherList[i];
-    }
-  }
 }
 
-/// Base class for 64-bit `int` typed lists.
-abstract class JSBigIntArrayImpl extends JSIntArrayImpl {
+final class JSBigIntArrayImpl extends JSIntArrayImpl {
   JSBigIntArrayImpl(super._ref);
 
   @override
-  int get elementSizeInBytes => 8;
-}
-
-final class JSBigUint64ArrayImpl extends JSBigIntArrayImpl
-    implements Uint64List {
-  JSBigUint64ArrayImpl._(super._ref);
-
-  factory JSBigUint64ArrayImpl(int length) =>
-      JSBigUint64ArrayImpl._(_newDataView(length * 8));
-
-  factory JSBigUint64ArrayImpl.fromJSArray(WasmExternRef? jsArrayRef) =>
-      JSBigUint64ArrayImpl._(_dataViewFromJSArray(jsArrayRef));
-
-  factory JSBigUint64ArrayImpl.view(
-      JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
-    _offsetAlignmentCheck(offsetInBytes, Uint64List.bytesPerElement);
-    final lengthInBytes = (length == null
-        ? ((buffer.lengthInBytes - offsetInBytes) & -8)
-        : length * 8);
-    return JSBigUint64ArrayImpl._(buffer.view(offsetInBytes, lengthInBytes));
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get length => lengthInBytes >>> 3;
-
-  @override
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]) => js.JS<
-          WasmExternRef?>(
-      '(o, start, length) => new BigUint64Array(o.buffer, o.byteOffset + start, length)',
-      toExternRef,
-      WasmI32.fromInt(start * 8),
-      WasmI32.fromInt(length ?? (this.length - start)));
-
-  @override
   @pragma("wasm:prefer-inline")
   int operator [](int index) {
-    _indexCheck(index, length);
-    return _getBigUint64(toExternRef, index * 8, true);
+    IndexError.check(index, length);
+    return js.JS<int>('(o, i) => o[i]', toExternRef, index.toDouble()).toInt();
   }
 
   @override
   @pragma("wasm:prefer-inline")
   void operator []=(int index, int value) {
-    _indexCheck(index, length);
-    return _setBigUint64(toExternRef, index * 8, value, true);
+    IndexError.check(index, length);
+    js.JS<void>('(o, i, v) => o[i] = v', toExternRef, index.toDouble(), value);
+  }
+}
+
+final class JSBigUint64ArrayImpl extends JSBigIntArrayImpl
+    implements Uint64List {
+  JSBigUint64ArrayImpl(super._ref);
+
+  factory JSBigUint64ArrayImpl.view(
+      JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
+    _offsetAlignmentCheck(offsetInBytes, Uint64List.bytesPerElement);
+    length ??= _adjustLength(buffer, offsetInBytes, Uint64List.bytesPerElement);
+    WasmExternRef? jsBuffer = js.JS<WasmExternRef?>(
+        '(b, o, l) => new BigUint64Array(b, o, l)',
+        buffer.toExternRef,
+        offsetInBytes.toDouble(),
+        length.toDouble());
+    return JSBigUint64ArrayImpl(jsBuffer);
   }
 
   @override
@@ -849,56 +598,29 @@
 
   @override
   Uint64List sublist(int start, [int? end]) {
-    final int newOffset = offsetInBytes + (start * 8);
-    final int newEnd = end == null ? lengthInBytes : end * 8;
-    final int newLength = newEnd - newOffset;
-    RangeError.checkValidRange(newOffset ~/ 8, newEnd ~/ 8, lengthInBytes ~/ 8);
-    return JSBigUint64ArrayImpl._(buffer.cloneAsDataView(newOffset, newLength));
+    final stop = RangeError.checkValidRange(start, end, length);
+    final source = js.JS<WasmExternRef?>(
+        '(a, s, p) => new BigUint64Array(a.subarray(s, p))',
+        toExternRef,
+        start.toDouble(),
+        stop.toDouble());
+    return JSBigUint64ArrayImpl(source);
   }
 }
 
 final class JSBigInt64ArrayImpl extends JSBigIntArrayImpl implements Int64List {
-  JSBigInt64ArrayImpl._(super._ref);
-
-  factory JSBigInt64ArrayImpl(int length) =>
-      JSBigInt64ArrayImpl._(_newDataView(length * 8));
-
-  factory JSBigInt64ArrayImpl.fromJSArray(WasmExternRef? jsArrayRef) =>
-      JSBigInt64ArrayImpl._(_dataViewFromJSArray(jsArrayRef));
+  JSBigInt64ArrayImpl(super._ref);
 
   factory JSBigInt64ArrayImpl.view(
       JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
     _offsetAlignmentCheck(offsetInBytes, Int64List.bytesPerElement);
-    final lengthInBytes = (length == null
-        ? ((buffer.lengthInBytes - offsetInBytes) & -8)
-        : length * 8);
-    return JSBigInt64ArrayImpl._(buffer.view(offsetInBytes, lengthInBytes));
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get length => lengthInBytes >>> 3;
-
-  @override
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]) => js.JS<
-          WasmExternRef?>(
-      '(o, start, length) => new BigInt64Array(o.buffer, o.byteOffset + start, length)',
-      toExternRef,
-      WasmI32.fromInt(start * 8),
-      WasmI32.fromInt(length ?? (this.length - start)));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int operator [](int index) {
-    _indexCheck(index, length);
-    return _getBigInt64(toExternRef, index * 8, true);
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  void operator []=(int index, int value) {
-    _indexCheck(index, length);
-    _setBigInt64(toExternRef, index * 8, value, true);
+    length ??= _adjustLength(buffer, offsetInBytes, Int64List.bytesPerElement);
+    WasmExternRef? jsBuffer = js.JS<WasmExternRef?>(
+        '(b, o, l) => new BigInt64Array(b, o, l)',
+        buffer.toExternRef,
+        offsetInBytes.toDouble(),
+        length.toDouble());
+    return JSBigInt64ArrayImpl(jsBuffer);
   }
 
   @override
@@ -906,20 +628,36 @@
 
   @override
   Int64List sublist(int start, [int? end]) {
-    final int newOffset = offsetInBytes + (start * 8);
-    final int newEnd = end == null ? lengthInBytes : end * 8;
-    final int newLength = newEnd - newOffset;
-    RangeError.checkValidRange(newOffset ~/ 8, newEnd ~/ 8, lengthInBytes ~/ 8);
-    return JSBigInt64ArrayImpl._(buffer.cloneAsDataView(newOffset, newLength));
+    final stop = RangeError.checkValidRange(start, end, length);
+    final source = js.JS<WasmExternRef?>(
+        '(a, s, p) => new BigInt64Array(a.subarray(s, p))',
+        toExternRef,
+        start.toDouble(),
+        stop.toDouble());
+    return JSBigInt64ArrayImpl(source);
   }
 }
 
-/// Base class for `double` typed lists.
-abstract class JSFloatArrayImpl extends JSArrayBase
+final class JSFloatArrayImpl extends JSArrayBufferViewImpl
     with ListMixin<double>, FixedLengthListMixin<double> {
   JSFloatArrayImpl(super._ref);
 
   @override
+  @pragma("wasm:prefer-inline")
+  double operator [](int index) {
+    IndexError.check(index, length);
+    return js.JS<double>('(o, i) => o[i]', toExternRef, index.toDouble());
+  }
+
+  @override
+  @pragma("wasm:prefer-inline")
+  void operator []=(int index, double value) {
+    IndexError.check(index, length);
+    js.JS<void>('(o, i, v) => o[i] = v', toExternRef, index.toDouble(),
+        value.toDouble());
+  }
+
+  @override
   void setAll(int index, Iterable<double> iterable) {
     final end = iterable.length + index;
     setRange(index, end, iterable);
@@ -928,80 +666,48 @@
   @override
   void setRange(int start, int end, Iterable<double> iterable,
       [int skipCount = 0]) {
+    int count = end - start;
     RangeError.checkValidRange(start, end, length);
 
-    if (skipCount < 0) {
-      throw ArgumentError(skipCount);
-    }
+    if (skipCount < 0) throw ArgumentError(skipCount);
 
-    if (iterable is JSArrayBase) {
-      final JSArrayBase source = unsafeCast<JSArrayBase>(iterable);
-      final length = end - start;
-      final sourceArray = source.toJSArrayExternRef(skipCount, length);
-      final targetArray = toJSArrayExternRef(start, length);
-      return _setRangeFast(targetArray, sourceArray);
-    }
-
-    List<double> otherList = iterable.skip(skipCount).toList(growable: false);
-
-    int count = end - start;
-    if (otherList.length < count) {
+    int sourceLength = iterable.length;
+    if (sourceLength - skipCount < count) {
       throw IterableElementError.tooFew();
     }
 
-    // TODO(omersa): Use unchecked operations here.
-    for (int i = 0, j = start; i < count; i++, j++) {
-      this[j] = otherList[i];
+    if (iterable is JSArrayBufferViewImpl) {
+      _setRangeFast(this, start, end, count, iterable as JSArrayBufferViewImpl,
+          sourceLength, skipCount);
+    } else {
+      List<double> otherList;
+      int otherStart;
+      if (iterable is List<double>) {
+        otherList = iterable;
+        otherStart = skipCount;
+      } else {
+        otherList = iterable.skip(skipCount).toList(growable: false);
+        otherStart = 0;
+      }
+      Lists.copy(otherList, otherStart, this, start, count);
     }
   }
 }
 
 final class JSFloat32ArrayImpl extends JSFloatArrayImpl implements Float32List {
-  JSFloat32ArrayImpl._(super._ref);
-
-  factory JSFloat32ArrayImpl(int length) =>
-      JSFloat32ArrayImpl._(_newDataView(length * 4));
-
-  factory JSFloat32ArrayImpl.fromJSArray(WasmExternRef? jsArrayRef) =>
-      JSFloat32ArrayImpl._(_dataViewFromJSArray(jsArrayRef));
+  JSFloat32ArrayImpl(super._ref);
 
   factory JSFloat32ArrayImpl.view(
       JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
     _offsetAlignmentCheck(offsetInBytes, Float32List.bytesPerElement);
-    final lengthInBytes = (length == null
-        ? ((buffer.lengthInBytes - offsetInBytes) & -4)
-        : length * 4);
-    return JSFloat32ArrayImpl._(buffer.view(offsetInBytes, lengthInBytes));
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get length => lengthInBytes >>> 2;
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get elementSizeInBytes => 4;
-
-  @override
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]) => js.JS<
-          WasmExternRef?>(
-      '(o, start, length) => new Float32Array(o.buffer, o.byteOffset + start, length)',
-      toExternRef,
-      WasmI32.fromInt(start * 4),
-      WasmI32.fromInt(length ?? (this.length - start)));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  double operator [](int index) {
-    _indexCheck(index, length);
-    return _getFloat32(toExternRef, index * 4, true);
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  void operator []=(int index, double value) {
-    _indexCheck(index, length);
-    _setFloat32(toExternRef, index * 4, value, true);
+    length ??=
+        _adjustLength(buffer, offsetInBytes, Float32List.bytesPerElement);
+    WasmExternRef? jsBuffer = js.JS<WasmExternRef?>(
+        '(b, o, l) => new Float32Array(b, o, l)',
+        buffer.toExternRef,
+        offsetInBytes.toDouble(),
+        length.toDouble());
+    return JSFloat32ArrayImpl(jsBuffer);
   }
 
   @override
@@ -1009,60 +715,30 @@
 
   @override
   Float32List sublist(int start, [int? end]) {
-    final int newOffset = offsetInBytes + (start * 4);
-    final int newEnd = end == null ? lengthInBytes : end * 4;
-    final int newLength = newEnd - newOffset;
-    RangeError.checkValidRange(newOffset ~/ 4, newEnd ~/ 4, lengthInBytes ~/ 4);
-    return JSFloat32ArrayImpl._(buffer.cloneAsDataView(newOffset, newLength));
+    final stop = RangeError.checkValidRange(start, end, length);
+    final source = js.JS<WasmExternRef?>(
+        '(a, s, p) => new Float32Array(a.subarray(s, p))',
+        toExternRef,
+        start.toDouble(),
+        stop.toDouble());
+    return JSFloat32ArrayImpl(source);
   }
 }
 
 final class JSFloat64ArrayImpl extends JSFloatArrayImpl implements Float64List {
-  JSFloat64ArrayImpl._(super._ref);
-
-  factory JSFloat64ArrayImpl(int length) =>
-      JSFloat64ArrayImpl._(_newDataView(length * 8));
-
-  factory JSFloat64ArrayImpl.fromJSArray(WasmExternRef? jsArrayRef) =>
-      JSFloat64ArrayImpl._(_dataViewFromJSArray(jsArrayRef));
+  JSFloat64ArrayImpl(super._ref);
 
   factory JSFloat64ArrayImpl.view(
       JSArrayBufferImpl buffer, int offsetInBytes, int? length) {
     _offsetAlignmentCheck(offsetInBytes, Float64List.bytesPerElement);
-    final lengthInBytes = (length == null
-        ? ((buffer.lengthInBytes - offsetInBytes) & -8)
-        : length * 8);
-    return JSFloat64ArrayImpl._(buffer.view(offsetInBytes, lengthInBytes));
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get length => lengthInBytes >>> 3;
-
-  @override
-  @pragma("wasm:prefer-inline")
-  int get elementSizeInBytes => 8;
-
-  @override
-  WasmExternRef? toJSArrayExternRef([int start = 0, int? length]) => js.JS<
-          WasmExternRef?>(
-      '(o, start, length) => new Float64Array(o.buffer, o.byteOffset + start, length)',
-      toExternRef,
-      WasmI32.fromInt(start * 8),
-      WasmI32.fromInt(length ?? (this.length - start)));
-
-  @override
-  @pragma("wasm:prefer-inline")
-  double operator [](int index) {
-    _indexCheck(index, length);
-    return _getFloat64(toExternRef, index * 8, true);
-  }
-
-  @override
-  @pragma("wasm:prefer-inline")
-  void operator []=(int index, double value) {
-    _indexCheck(index, length);
-    _setFloat64(toExternRef, index * 8, value, true);
+    length ??=
+        _adjustLength(buffer, offsetInBytes, Float64List.bytesPerElement);
+    WasmExternRef? jsBuffer = js.JS<WasmExternRef?>(
+        '(b, o, l) => new Float64Array(b, o, l)',
+        buffer.toExternRef,
+        offsetInBytes.toDouble(),
+        length.toDouble());
+    return JSFloat64ArrayImpl(jsBuffer);
   }
 
   @override
@@ -1070,11 +746,13 @@
 
   @override
   Float64List sublist(int start, [int? end]) {
-    final int newOffset = offsetInBytes + (start * 8);
-    final int newEnd = end == null ? lengthInBytes : end * 8;
-    final int newLength = newEnd - newOffset;
-    RangeError.checkValidRange(newOffset ~/ 8, newEnd ~/ 8, lengthInBytes ~/ 8);
-    return JSFloat64ArrayImpl._(buffer.cloneAsDataView(newOffset, newLength));
+    final stop = RangeError.checkValidRange(start, end, length);
+    final source = js.JS<WasmExternRef?>(
+        '(a, s, p) => new Float64Array(a.subarray(s, p))',
+        toExternRef,
+        start.toDouble(),
+        stop.toDouble());
+    return JSFloat64ArrayImpl(source);
   }
 }
 
@@ -1090,7 +768,6 @@
   ByteBuffer get buffer => _storage.buffer;
 
   @override
-  @pragma("wasm:prefer-inline")
   int get lengthInBytes => _storage.lengthInBytes;
 
   @override
@@ -1100,13 +777,12 @@
   int get elementSizeInBytes => Float32x4List.bytesPerElement;
 
   @override
-  @pragma("wasm:prefer-inline")
   int get length => _storage.length ~/ 4;
 
   @override
   @pragma("wasm:prefer-inline")
   Float32x4 operator [](int index) {
-    _indexCheck(index, length);
+    IndexError.check(index, length);
     double _x = _storage[(index * 4) + 0];
     double _y = _storage[(index * 4) + 1];
     double _z = _storage[(index * 4) + 2];
@@ -1117,7 +793,7 @@
   @override
   @pragma("wasm:prefer-inline")
   void operator []=(int index, Float32x4 value) {
-    _indexCheck(index, length);
+    IndexError.check(index, length);
     _storage[(index * 4) + 0] = value.x;
     _storage[(index * 4) + 1] = value.y;
     _storage[(index * 4) + 2] = value.z;
@@ -1133,35 +809,6 @@
     return JSFloat32x4ArrayImpl.externalStorage(
         _storage.sublist(start * 4, stop * 4) as JSFloat32ArrayImpl);
   }
-
-  @override
-  void setAll(int index, Iterable<Float32x4> iterable) {
-    final end = iterable.length + index;
-    setRange(index, end, iterable);
-  }
-
-  @override
-  void setRange(int start, int end, Iterable<Float32x4> iterable,
-      [int skipCount = 0]) {
-    RangeError.checkValidRange(start, end, length);
-
-    if (skipCount < 0) {
-      throw ArgumentError(skipCount);
-    }
-
-    List<Float32x4> otherList =
-        iterable.skip(skipCount).toList(growable: false);
-
-    int count = end - start;
-    if (otherList.length < count) {
-      throw IterableElementError.tooFew();
-    }
-
-    // TODO(omersa): Use unchecked operations here.
-    for (int i = 0, j = start; i < count; i++, j++) {
-      this[j] = otherList[i];
-    }
-  }
 }
 
 final class JSFloat64x2ArrayImpl
@@ -1176,7 +823,6 @@
   ByteBuffer get buffer => _storage.buffer;
 
   @override
-  @pragma("wasm:prefer-inline")
   int get lengthInBytes => _storage.lengthInBytes;
 
   @override
@@ -1186,13 +832,12 @@
   int get elementSizeInBytes => Float64x2List.bytesPerElement;
 
   @override
-  @pragma("wasm:prefer-inline")
   int get length => _storage.length ~/ 2;
 
   @override
   @pragma("wasm:prefer-inline")
   Float64x2 operator [](int index) {
-    _indexCheck(index, length);
+    IndexError.check(index, length);
     double _x = _storage[(index * 2) + 0];
     double _y = _storage[(index * 2) + 1];
     return Float64x2(_x, _y);
@@ -1201,7 +846,7 @@
   @override
   @pragma("wasm:prefer-inline")
   void operator []=(int index, Float64x2 value) {
-    _indexCheck(index, length);
+    IndexError.check(index, length);
     _storage[(index * 2) + 0] = value.x;
     _storage[(index * 2) + 1] = value.y;
   }
@@ -1215,46 +860,27 @@
     return JSFloat64x2ArrayImpl.externalStorage(
         _storage.sublist(start * 2, stop * 2) as JSFloat64ArrayImpl);
   }
-
-  @override
-  void setAll(int index, Iterable<Float64x2> iterable) {
-    final end = iterable.length + index;
-    setRange(index, end, iterable);
-  }
-
-  @override
-  void setRange(int start, int end, Iterable<Float64x2> iterable,
-      [int skipCount = 0]) {
-    RangeError.checkValidRange(start, end, length);
-
-    if (skipCount < 0) {
-      throw ArgumentError(skipCount);
-    }
-
-    List<Float64x2> otherList =
-        iterable.skip(skipCount).toList(growable: false);
-
-    int count = end - start;
-    if (otherList.length < count) {
-      throw IterableElementError.tooFew();
-    }
-
-    // TODO(omersa): Use unchecked operations here.
-    for (int i = 0, j = start; i < count; i++, j++) {
-      this[j] = otherList[i];
-    }
-  }
 }
 
-@pragma("wasm:prefer-inline")
-void _indexCheck(int index, int length) {
-  if (WasmI64.fromInt(length).leU(WasmI64.fromInt(index))) {
-    throw IndexError.withLength(index, length);
+void _setRangeFast(JSArrayBufferViewImpl target, int start, int end, int count,
+    JSArrayBufferViewImpl source, int sourceLength, int skipCount) {
+  WasmExternRef? jsSource;
+  if (skipCount != 0 || sourceLength != count) {
+    // Create a view of the exact subrange that is copied from the source.
+    jsSource = js.JS<WasmExternRef?>(
+        '(s, k, e) => s.subarray(k, e)',
+        source.toExternRef,
+        skipCount.toDouble(),
+        (skipCount + count).toDouble());
+  } else {
+    jsSource = source.toExternRef;
   }
+  js.JS<void>('(t, s, i) => t.set(s, i)', target.toExternRef, jsSource,
+      start.toDouble());
 }
 
-void _setRangeFast(WasmExternRef? targetArray, WasmExternRef? sourceArray) =>
-    js.JS<void>('(t, s) => t.set(s)', targetArray, sourceArray);
+int _adjustLength(ByteBuffer buffer, int offsetInBytes, int bytesPerElement) =>
+    (buffer.lengthInBytes - offsetInBytes) ~/ bytesPerElement;
 
 void _offsetAlignmentCheck(int offset, int alignment) {
   if ((offset % alignment) != 0) {
@@ -1262,196 +888,3 @@
         'bytesPerElement ($alignment)');
   }
 }
-
-WasmExternRef? _newDataView(int length) => js.JS<WasmExternRef?>(
-    'l => new DataView(new ArrayBuffer(l))', WasmI32.fromInt(length));
-
-WasmExternRef? _dataViewFromJSArray(WasmExternRef? jsArrayRef) =>
-    js.JS<WasmExternRef?>(
-        '(o) => new DataView(o.buffer, o.byteOffset, o.byteLength)',
-        jsArrayRef);
-
-@pragma("wasm:prefer-inline")
-int _arrayBufferByteLength(WasmExternRef? ref) =>
-    js.JS<WasmI32>('o => o.byteLength', ref).toIntSigned();
-
-WasmExternRef? _dataViewBuffer(WasmExternRef? dataViewRef) =>
-    js.JS<WasmExternRef?>('o => o.buffer', dataViewRef);
-
-@pragma("wasm:prefer-inline")
-int _dataViewByteOffset(WasmExternRef? dataViewRef) =>
-    js.JS<WasmI32>('o => o.byteOffset', dataViewRef).toIntSigned();
-
-@pragma("wasm:prefer-inline")
-int _dataViewByteLength(WasmExternRef? ref) => js
-    .JS<WasmF64>(
-        "Function.prototype.call.bind(Object.getOwnPropertyDescriptor(DataView.prototype, 'byteLength').get)",
-        ref)
-    .truncSatS()
-    .toInt();
-
-@pragma("wasm:prefer-inline")
-WasmExternRef? _newDataViewFromArrayBuffer(
-        WasmExternRef? bufferRef, int offsetInBytes, int? length) =>
-    length == null
-        ? js.JS<WasmExternRef?>('(b, o) => new DataView(b, o)', bufferRef,
-            WasmI32.fromInt(offsetInBytes))
-        : js.JS<WasmExternRef?>('(b, o, l) => new DataView(b, o, l)', bufferRef,
-            WasmI32.fromInt(offsetInBytes), WasmI32.fromInt(length));
-
-@pragma("wasm:prefer-inline")
-int _getUint8(WasmExternRef? ref, int byteOffset) => js
-    .JS<WasmI32>('Function.prototype.call.bind(DataView.prototype.getUint8)',
-        ref, WasmI32.fromInt(byteOffset))
-    .toIntUnsigned();
-
-@pragma("wasm:prefer-inline")
-void _setUint8(WasmExternRef? ref, int byteOffset, int value) => js.JS<void>(
-    'Function.prototype.call.bind(DataView.prototype.setUint8)',
-    ref,
-    WasmI32.fromInt(byteOffset),
-    WasmI32.fromInt(value));
-
-@pragma("wasm:prefer-inline")
-int _getInt8(WasmExternRef? ref, int byteOffset) => js
-    .JS<WasmI32>('Function.prototype.call.bind(DataView.prototype.getInt8)',
-        ref, WasmI32.fromInt(byteOffset))
-    .toIntSigned();
-
-@pragma("wasm:prefer-inline")
-void _setInt8(WasmExternRef? ref, int byteOffset, int value) => js.JS<void>(
-    'Function.prototype.call.bind(DataView.prototype.setInt8)',
-    ref,
-    WasmI32.fromInt(byteOffset),
-    WasmI32.fromInt(value));
-
-@pragma("wasm:prefer-inline")
-int _getUint16(WasmExternRef? ref, int byteOffset, bool littleEndian) => js
-    .JS<WasmI32>('Function.prototype.call.bind(DataView.prototype.getUint16)',
-        ref, WasmI32.fromInt(byteOffset), WasmI32.fromBool(littleEndian))
-    .toIntUnsigned();
-
-@pragma("wasm:prefer-inline")
-void _setUint16(
-        WasmExternRef? ref, int byteOffset, int value, bool littleEndian) =>
-    js.JS<void>(
-        'Function.prototype.call.bind(DataView.prototype.setUint16)',
-        ref,
-        WasmI32.fromInt(byteOffset),
-        WasmI32.fromInt(value),
-        WasmI32.fromBool(littleEndian));
-
-@pragma("wasm:prefer-inline")
-int _getInt16(WasmExternRef? ref, int byteOffset, bool littleEndian) => js
-    .JS<WasmI32>('Function.prototype.call.bind(DataView.prototype.getInt16)',
-        ref, WasmI32.fromInt(byteOffset), WasmI32.fromBool(littleEndian))
-    .toIntSigned();
-
-@pragma("wasm:prefer-inline")
-void _setInt16(
-        WasmExternRef? ref, int byteOffset, int value, bool littleEndian) =>
-    js.JS<void>(
-        'Function.prototype.call.bind(DataView.prototype.setInt16)',
-        ref,
-        WasmI32.fromInt(byteOffset),
-        WasmI32.fromInt(value),
-        WasmI32.fromBool(littleEndian));
-
-@pragma("wasm:prefer-inline")
-int _getUint32(WasmExternRef? ref, int byteOffset, bool littleEndian) => js
-    .JS<WasmI32>('Function.prototype.call.bind(DataView.prototype.getUint32)',
-        ref, WasmI32.fromInt(byteOffset), WasmI32.fromBool(littleEndian))
-    .toIntUnsigned();
-
-@pragma("wasm:prefer-inline")
-void _setUint32(
-        WasmExternRef? ref, int byteOffset, int value, bool littleEndian) =>
-    js.JS<void>(
-        'Function.prototype.call.bind(DataView.prototype.setUint32)',
-        ref,
-        WasmI32.fromInt(byteOffset),
-        WasmI32.fromInt(value),
-        WasmI32.fromBool(littleEndian));
-
-@pragma("wasm:prefer-inline")
-int _getInt32(WasmExternRef? ref, int byteOffset, bool littleEndian) => js
-    .JS<WasmI32>('Function.prototype.call.bind(DataView.prototype.getInt32)',
-        ref, WasmI32.fromInt(byteOffset), WasmI32.fromBool(littleEndian))
-    .toIntSigned();
-
-@pragma("wasm:prefer-inline")
-void _setInt32(
-        WasmExternRef? ref, int byteOffset, int value, bool littleEndian) =>
-    js.JS<void>(
-        'Function.prototype.call.bind(DataView.prototype.setInt32)',
-        ref,
-        WasmI32.fromInt(byteOffset),
-        WasmI32.fromInt(value),
-        WasmI32.fromBool(littleEndian));
-
-@pragma("wasm:prefer-inline")
-int _getBigUint64(WasmExternRef? ref, int byteOffset, bool littleEndian) => js
-    .JS<WasmI64>(
-        'Function.prototype.call.bind(DataView.prototype.getBigUint64)',
-        ref,
-        WasmI32.fromInt(byteOffset),
-        WasmI32.fromBool(littleEndian))
-    .toInt();
-
-@pragma("wasm:prefer-inline")
-void _setBigUint64(
-        WasmExternRef? ref, int byteOffset, int value, bool littleEndian) =>
-    js.JS<void>(
-        'Function.prototype.call.bind(DataView.prototype.setBigUint64)',
-        ref,
-        WasmI32.fromInt(byteOffset),
-        WasmI64.fromInt(value),
-        WasmI32.fromBool(littleEndian));
-
-@pragma("wasm:prefer-inline")
-int _getBigInt64(WasmExternRef? ref, int byteOffset, bool littleEndian) => js
-    .JS<WasmI64>('Function.prototype.call.bind(DataView.prototype.getBigInt64)',
-        ref, WasmI32.fromInt(byteOffset), WasmI32.fromBool(littleEndian))
-    .toInt();
-
-@pragma("wasm:prefer-inline")
-void _setBigInt64(
-        WasmExternRef? ref, int byteOffset, int value, bool littleEndian) =>
-    js.JS<void>(
-        'Function.prototype.call.bind(DataView.prototype.setBigInt64)',
-        ref,
-        WasmI32.fromInt(byteOffset),
-        WasmI64.fromInt(value),
-        WasmI32.fromBool(littleEndian));
-
-@pragma("wasm:prefer-inline")
-double _getFloat32(WasmExternRef? ref, int byteOffset, bool littleEndian) => js
-    .JS<WasmF32>('Function.prototype.call.bind(DataView.prototype.getFloat32)',
-        ref, WasmI32.fromInt(byteOffset), WasmI32.fromBool(littleEndian))
-    .toDouble();
-
-@pragma("wasm:prefer-inline")
-void _setFloat32(
-        WasmExternRef? ref, int byteOffset, num value, bool littleEndian) =>
-    js.JS<void>(
-        'Function.prototype.call.bind(DataView.prototype.setFloat32)',
-        ref,
-        WasmI32.fromInt(byteOffset),
-        WasmF32.fromDouble(value.toDouble()),
-        WasmI32.fromBool(littleEndian));
-
-@pragma("wasm:prefer-inline")
-double _getFloat64(WasmExternRef? ref, int byteOffset, bool littleEndian) => js
-    .JS<WasmF64>('Function.prototype.call.bind(DataView.prototype.getFloat64)',
-        ref, WasmI32.fromInt(byteOffset), WasmI32.fromBool(littleEndian))
-    .toDouble();
-
-@pragma("wasm:prefer-inline")
-void _setFloat64(
-        WasmExternRef? ref, int byteOffset, num value, bool littleEndian) =>
-    js.JS<void>(
-        'Function.prototype.call.bind(DataView.prototype.setFloat64)',
-        ref,
-        WasmI32.fromInt(byteOffset),
-        WasmF64.fromDouble(value.toDouble()),
-        WasmI32.fromBool(littleEndian));
diff --git a/sdk/lib/_internal/wasm/lib/js_types.dart b/sdk/lib/_internal/wasm/lib/js_types.dart
index 7e75fcb..54bed49 100644
--- a/sdk/lib/_internal/wasm/lib/js_types.dart
+++ b/sdk/lib/_internal/wasm/lib/js_types.dart
@@ -24,7 +24,6 @@
         Sort,
         SubListIterable,
         TakeWhileIterable,
-        unsafeCast,
         WhereIterable,
         WhereTypeIterable;
 import 'dart:_js_helper' as js;
diff --git a/sdk/lib/_internal/wasm/lib/simd_patch.dart b/sdk/lib/_internal/wasm/lib/simd_patch.dart
index 883f29d..50c55da 100644
--- a/sdk/lib/_internal/wasm/lib/simd_patch.dart
+++ b/sdk/lib/_internal/wasm/lib/simd_patch.dart
@@ -10,6 +10,57 @@
 // TODO(joshualitt): Implement SIMD intrinsics and delete this patch.
 
 @patch
+class Int32x4List {
+  @patch
+  factory Int32x4List(int length) = NaiveInt32x4List;
+
+  @patch
+  factory Int32x4List.fromList(List<Int32x4> elements) =
+      NaiveInt32x4List.fromList;
+}
+
+@patch
+class Float32x4List {
+  @patch
+  factory Float32x4List(int length) = NaiveFloat32x4List;
+
+  @patch
+  factory Float32x4List.fromList(List<Float32x4> elements) =
+      NaiveFloat32x4List.fromList;
+}
+
+@patch
+class Float64x2List {
+  @patch
+  factory Float64x2List(int length) = NaiveFloat64x2List;
+
+  @patch
+  factory Float64x2List.fromList(List<Float64x2> elements) =
+      NaiveFloat64x2List.fromList;
+}
+
+@patch
+abstract class UnmodifiableInt32x4ListView implements Int32x4List {
+  @patch
+  factory UnmodifiableInt32x4ListView(Int32x4List list) =>
+      NaiveUnmodifiableInt32x4List(list);
+}
+
+@patch
+abstract class UnmodifiableFloat32x4ListView implements Float32x4List {
+  @patch
+  factory UnmodifiableFloat32x4ListView(Float32x4List list) =>
+      NaiveUnmodifiableFloat32x4List(list);
+}
+
+@patch
+abstract class UnmodifiableFloat64x2ListView implements Float64x2List {
+  @patch
+  factory UnmodifiableFloat64x2ListView(Float64x2List list) =>
+      NaiveUnmodifiableFloat64x2List(list);
+}
+
+@patch
 class Int32x4 {
   @patch
   factory Int32x4(int x, int y, int z, int w) = NaiveInt32x4;
diff --git a/sdk/lib/_internal/wasm/lib/typed_data_patch.dart b/sdk/lib/_internal/wasm/lib/typed_data_patch.dart
index 7cfa118..4f3dc64 100644
--- a/sdk/lib/_internal/wasm/lib/typed_data_patch.dart
+++ b/sdk/lib/_internal/wasm/lib/typed_data_patch.dart
@@ -3,7 +3,6 @@
 // BSD-style license that can be found in the LICENSE file.
 
 import 'dart:_internal' show patch, unsafeCast;
-import 'dart:_simd';
 import 'dart:_typed_data';
 import 'dart:_wasm';
 
@@ -274,54 +273,3 @@
       // immutable, implement it in all `ByteData` subtypes.
       unsafeCast<ByteDataBase>(data).immutable();
 }
-
-@patch
-class Int32x4List {
-  @patch
-  factory Int32x4List(int length) = NaiveInt32x4List;
-
-  @patch
-  factory Int32x4List.fromList(List<Int32x4> elements) =
-      NaiveInt32x4List.fromList;
-}
-
-@patch
-class Float32x4List {
-  @patch
-  factory Float32x4List(int length) = NaiveFloat32x4List;
-
-  @patch
-  factory Float32x4List.fromList(List<Float32x4> elements) =
-      NaiveFloat32x4List.fromList;
-}
-
-@patch
-class Float64x2List {
-  @patch
-  factory Float64x2List(int length) = NaiveFloat64x2List;
-
-  @patch
-  factory Float64x2List.fromList(List<Float64x2> elements) =
-      NaiveFloat64x2List.fromList;
-}
-
-@patch
-abstract class UnmodifiableInt32x4ListView implements Int32x4List {
-  @patch
-  factory UnmodifiableInt32x4ListView(Int32x4List list) =>
-      NaiveUnmodifiableInt32x4List(list);
-}
-
-@patch
-abstract class UnmodifiableFloat32x4ListView implements Float32x4List {
-  @patch
-  factory UnmodifiableFloat32x4ListView(Float32x4List list) =>
-      NaiveUnmodifiableFloat32x4List(list);
-}
-
-@patch
-abstract class UnmodifiableFloat64x2ListView implements Float64x2List {
-  @patch
-  factory UnmodifiableFloat64x2ListView(Float64x2List list) =>
-      NaiveUnmodifiableFloat64x2List(list);
-}
diff --git a/sdk/lib/_internal/wasm_js_compatibility/lib/string_patch.dart b/sdk/lib/_internal/wasm_js_compatibility/lib/string_patch.dart
index 5c8f2ed..23e2052 100644
--- a/sdk/lib/_internal/wasm_js_compatibility/lib/string_patch.dart
+++ b/sdk/lib/_internal/wasm_js_compatibility/lib/string_patch.dart
@@ -55,13 +55,14 @@
     // Create JS string from `list`.
     const kMaxApply = 500;
     if (index <= kMaxApply) {
-      return _fromCharCodeApplySubarray(list, 0, index);
+      return _fromCharCodeApplySubarray(list.toExternRef, 0, index.toDouble());
     }
 
     String result = '';
     for (int i = 0; i < index; i += kMaxApply) {
       final chunkEnd = (i + kMaxApply < index) ? i + kMaxApply : index;
-      result += _fromCharCodeApplySubarray(list, i, chunkEnd);
+      result += _fromCharCodeApplySubarray(
+          list.toExternRef, i.toDouble(), chunkEnd.toDouble());
     }
     return result;
   }
@@ -92,11 +93,10 @@
   }
 
   static String _fromCharCodeApplySubarray(
-      JSUint32ArrayImpl charCodes, int index, int end) {
-    return JSStringImpl(js.JS<WasmExternRef?>(
-        '(c, i, e) => String.fromCharCode.apply(null, new Uint32Array(c.buffer, c.byteOffset + i, e))',
-        charCodes.toExternRef,
-        WasmI32.fromInt(index * 4),
-        WasmI32.fromInt(end - index)));
-  }
+          WasmExternRef? charCodes, double index, double end) =>
+      JSStringImpl(js.JS<WasmExternRef?>(
+          '(c, i, e) => String.fromCharCode.apply(null, c.subarray(i, e))',
+          charCodes,
+          index,
+          end));
 }
diff --git a/sdk/lib/_internal/wasm_js_compatibility/lib/typed_data_patch.dart b/sdk/lib/_internal/wasm_js_compatibility/lib/typed_data_patch.dart
index 4ad4f22..f50f57a 100644
--- a/sdk/lib/_internal/wasm_js_compatibility/lib/typed_data_patch.dart
+++ b/sdk/lib/_internal/wasm_js_compatibility/lib/typed_data_patch.dart
@@ -2,164 +2,227 @@
 // 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 'dart:_internal' show patch;
+import 'dart:_internal' show FixedLengthListMixin, patch, UnmodifiableListBase;
+import 'dart:_js_helper' as js;
 import 'dart:_js_types';
+import 'dart:_string_helper';
+import 'dart:_wasm';
 import 'dart:typed_data';
+import 'dart:js_interop';
+
+// TODO(joshualitt): Optimizations for this file:
+//   * Move list to JS and allocate on the JS side for `fromLength`
+//     constructors.
 
 @patch
 class ByteData {
   @patch
-  factory ByteData(int length) = JSDataViewImpl;
+  factory ByteData(int length) {
+    return JSDataViewImpl(js.JS<WasmExternRef?>(
+        'l => new DataView(new ArrayBuffer(l))', length.toDouble()));
+  }
 }
 
 @patch
 class Uint8List {
   @patch
-  factory Uint8List(int length) = JSUint8ArrayImpl;
+  factory Uint8List(int length) {
+    return JSUint8ArrayImpl(
+        js.JS<WasmExternRef?>('l => new Uint8Array(l)', length.toDouble()));
+  }
 
   @patch
   factory Uint8List.fromList(List<int> elements) =>
-      JSUint8ArrayImpl(elements.length)..setRange(0, elements.length, elements);
+      Uint8List(elements.length)..setRange(0, elements.length, elements);
 }
 
 @patch
 class Int8List {
   @patch
-  factory Int8List(int length) = JSInt8ArrayImpl;
+  factory Int8List(int length) {
+    return JSInt8ArrayImpl(
+        js.JS<WasmExternRef?>('l => new Int8Array(l)', length.toDouble()));
+  }
 
   @patch
   factory Int8List.fromList(List<int> elements) =>
-      JSInt8ArrayImpl(elements.length)..setRange(0, elements.length, elements);
+      Int8List(elements.length)..setRange(0, elements.length, elements);
 }
 
 @patch
 class Uint8ClampedList {
   @patch
-  factory Uint8ClampedList(int length) = JSUint8ClampedArrayImpl;
+  factory Uint8ClampedList(int length) {
+    return JSUint8ClampedArrayImpl(js.JS<WasmExternRef?>(
+        'l => new Uint8ClampedArray(l)', length.toDouble()));
+  }
 
   @patch
   factory Uint8ClampedList.fromList(List<int> elements) =>
-      JSUint8ClampedArrayImpl(elements.length)
-        ..setRange(0, elements.length, elements);
+      Uint8ClampedList(elements.length)..setRange(0, elements.length, elements);
 }
 
 @patch
 class Uint16List {
   @patch
-  factory Uint16List(int length) = JSUint16ArrayImpl;
+  factory Uint16List(int length) {
+    return JSUint16ArrayImpl(
+        js.JS<WasmExternRef?>('l => new Uint16Array(l)', length.toDouble()));
+  }
 
   @patch
   factory Uint16List.fromList(List<int> elements) =>
-      JSUint16ArrayImpl(elements.length)
-        ..setRange(0, elements.length, elements);
+      Uint16List(elements.length)..setRange(0, elements.length, elements);
 }
 
 @patch
 class Int16List {
   @patch
-  factory Int16List(int length) = JSInt16ArrayImpl;
+  factory Int16List(int length) {
+    return JSInt16ArrayImpl(
+        js.JS<WasmExternRef?>('l => new Int16Array(l)', length.toDouble()));
+  }
 
   @patch
   factory Int16List.fromList(List<int> elements) =>
-      JSInt16ArrayImpl(elements.length)..setRange(0, elements.length, elements);
+      Int16List(elements.length)..setRange(0, elements.length, elements);
 }
 
 @patch
 class Uint32List {
   @patch
-  factory Uint32List(int length) = JSUint32ArrayImpl;
+  factory Uint32List(int length) {
+    return JSUint32ArrayImpl(
+        js.JS<WasmExternRef?>('l => new Uint32Array(l)', length.toDouble()));
+  }
 
   @patch
   factory Uint32List.fromList(List<int> elements) =>
-      JSUint32ArrayImpl(elements.length)
-        ..setRange(0, elements.length, elements);
+      Uint32List(elements.length)..setRange(0, elements.length, elements);
 }
 
 @patch
 class Int32List {
   @patch
-  factory Int32List(int length) = JSInt32ArrayImpl;
+  factory Int32List(int length) {
+    return JSInt32ArrayImpl(
+        js.JS<WasmExternRef?>('l => new Int32Array(l)', length.toDouble()));
+  }
 
   @patch
   factory Int32List.fromList(List<int> elements) =>
-      JSInt32ArrayImpl(elements.length)..setRange(0, elements.length, elements);
+      Int32List(elements.length)..setRange(0, elements.length, elements);
 }
 
 @patch
 class Int32x4List {
   @patch
-  factory Int32x4List(int length) =>
-      JSInt32x4ArrayImpl.externalStorage(JSInt32ArrayImpl(length * 4));
+  factory Int32x4List(int length) {
+    return JSInt32x4ArrayImpl.externalStorage(JSInt32ArrayImpl(js
+        .JS<WasmExternRef?>('l => new Int32Array(l * 4)', length.toDouble())));
+  }
 
   @patch
-  factory Int32x4List.fromList(List<Int32x4> elements) =>
-      Int32x4List(elements.length)..setRange(0, elements.length, elements);
+  factory Int32x4List.fromList(List<Int32x4> elements) {
+    final length = elements.length;
+    final l = Int32x4List(length);
+    for (var i = 0; i < length; i++) {
+      l[i] = elements[i];
+    }
+    return l;
+  }
 }
 
 @patch
 class Int64List {
   @patch
-  factory Int64List(int length) = JSBigInt64ArrayImpl;
+  factory Int64List(int length) {
+    return JSBigInt64ArrayImpl(
+        js.JS<WasmExternRef?>('l => new BigInt64Array(l)', length.toDouble()));
+  }
 
   @patch
   factory Int64List.fromList(List<int> elements) =>
-      JSBigInt64ArrayImpl(elements.length)
-        ..setRange(0, elements.length, elements);
+      Int64List(elements.length)..setRange(0, elements.length, elements);
 }
 
 @patch
 class Uint64List {
   @patch
-  factory Uint64List(int length) = JSBigUint64ArrayImpl;
+  factory Uint64List(int length) {
+    return JSBigUint64ArrayImpl(
+        js.JS<WasmExternRef?>('l => new BigUint64Array(l)', length.toDouble()));
+  }
 
   @patch
   factory Uint64List.fromList(List<int> elements) =>
-      JSBigUint64ArrayImpl(elements.length)
-        ..setRange(0, elements.length, elements);
+      Uint64List(elements.length)..setRange(0, elements.length, elements);
 }
 
 @patch
 class Float32List {
   @patch
-  factory Float32List(int length) = JSFloat32ArrayImpl;
+  factory Float32List(int length) {
+    return JSFloat32ArrayImpl(
+        js.JS<WasmExternRef?>('l => new Float32Array(l)', length.toDouble()));
+  }
 
   @patch
   factory Float32List.fromList(List<double> elements) =>
-      JSFloat32ArrayImpl(elements.length)
-        ..setRange(0, elements.length, elements);
+      Float32List(elements.length)..setRange(0, elements.length, elements);
 }
 
 @patch
 class Float32x4List {
   @patch
-  factory Float32x4List(int length) =>
-      JSFloat32x4ArrayImpl.externalStorage(JSFloat32ArrayImpl(length * 4));
+  factory Float32x4List(int length) {
+    return JSFloat32x4ArrayImpl.externalStorage(JSFloat32ArrayImpl(
+        js.JS<WasmExternRef?>(
+            'l => new Float32Array(l * 4)', length.toDouble())));
+  }
 
   @patch
-  factory Float32x4List.fromList(List<Float32x4> elements) =>
-      Float32x4List(elements.length)..setRange(0, elements.length, elements);
+  factory Float32x4List.fromList(List<Float32x4> elements) {
+    final length = elements.length;
+    final l = Float32x4List(length);
+    for (var i = 0; i < length; i++) {
+      l[i] = elements[i];
+    }
+    return l;
+  }
 }
 
 @patch
 class Float64List {
   @patch
-  factory Float64List(int length) = JSFloat64ArrayImpl;
+  factory Float64List(int length) {
+    return JSFloat64ArrayImpl(
+        js.JS<WasmExternRef?>('l => new Float64Array(l)', length.toDouble()));
+  }
 
   @patch
   factory Float64List.fromList(List<double> elements) =>
-      JSFloat64ArrayImpl(elements.length)
-        ..setRange(0, elements.length, elements);
+      Float64List(elements.length)..setRange(0, elements.length, elements);
 }
 
 @patch
 class Float64x2List {
   @patch
-  factory Float64x2List(int length) =>
-      JSFloat64x2ArrayImpl.externalStorage(JSFloat64ArrayImpl(length * 2));
+  factory Float64x2List(int length) {
+    return JSFloat64x2ArrayImpl.externalStorage(JSFloat64ArrayImpl(
+        js.JS<WasmExternRef?>(
+            'l => new Float64Array(l * 2)', length.toDouble())));
+  }
 
   @patch
-  factory Float64x2List.fromList(List<Float64x2> elements) =>
-      Float64x2List(elements.length)..setRange(0, elements.length, elements);
+  factory Float64x2List.fromList(List<Float64x2> elements) {
+    final length = elements.length;
+    final l = Float64x2List(length);
+    for (var i = 0; i < length; i++) {
+      l[i] = elements[i];
+    }
+    return l;
+  }
 }
 
 @patch
diff --git a/sdk/lib/_wasm/wasm_types.dart b/sdk/lib/_wasm/wasm_types.dart
index c618783..1933e54 100644
--- a/sdk/lib/_wasm/wasm_types.dart
+++ b/sdk/lib/_wasm/wasm_types.dart
@@ -151,11 +151,7 @@
   const WasmI64(this._value);
 
   external factory WasmI64.fromInt(int value);
-
   external int toInt();
-
-  /// `i64.le_u`.
-  external bool leU(WasmI64 other);
 }
 
 /// The Wasm `f32` type.
@@ -181,11 +177,7 @@
   const WasmF64(this._value);
 
   external factory WasmF64.fromDouble(double value);
-
   external double toDouble();
-
-  /// `i64.trunc_sat_f64_s`.
-  external WasmI64 truncSatS();
 }
 
 /// A Wasm array with integer element type.