Version 2.13.0-24.0.dev

Merge commit '7a4d1c118f3ede3b6301ad3c33e40edc249005cd' into 'dev'
diff --git a/DEPS b/DEPS
index 3316fb1..284573c 100644
--- a/DEPS
+++ b/DEPS
@@ -102,7 +102,7 @@
 
   "chromedriver_tag": "83.0.4103.39",
   "dartdoc_rev" : "9e61a4f11091aaa8998525a2692b14148dc24ab5",
-  "ffi_rev": "f288e906c92e2ab378768dfa61a40814ede7a2a5",
+  "ffi_rev": "53866b792f397113189bce3ea71e83b0e46b9cea",
   "fixnum_rev": "16d3890c6dc82ca629659da1934e412292508bba",
   "file_rev": "0e09370f581ab6388d46fda4cdab66638c0171a1",
   "glob_rev": "a62acf590598f458d3198d9f2930c1c9dd4b1379",
diff --git a/benchmarks/FfiBoringssl/dart/FfiBoringssl.dart b/benchmarks/FfiBoringssl/dart/FfiBoringssl.dart
index 3249be4..8781c43 100644
--- a/benchmarks/FfiBoringssl/dart/FfiBoringssl.dart
+++ b/benchmarks/FfiBoringssl/dart/FfiBoringssl.dart
@@ -11,7 +11,6 @@
 import 'package:benchmark_harness/benchmark_harness.dart';
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'digest.dart';
 import 'types.dart';
 
diff --git a/benchmarks/FfiBoringssl/dart/calloc.dart b/benchmarks/FfiBoringssl/dart/calloc.dart
deleted file mode 100644
index e17238a..0000000
--- a/benchmarks/FfiBoringssl/dart/calloc.dart
+++ /dev/null
@@ -1,109 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int? alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/benchmarks/FfiBoringssl/dart2/FfiBoringssl.dart b/benchmarks/FfiBoringssl/dart2/FfiBoringssl.dart
index c749745..635fa57 100644
--- a/benchmarks/FfiBoringssl/dart2/FfiBoringssl.dart
+++ b/benchmarks/FfiBoringssl/dart2/FfiBoringssl.dart
@@ -13,7 +13,6 @@
 import 'package:benchmark_harness/benchmark_harness.dart';
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'digest.dart';
 import 'types.dart';
 
diff --git a/benchmarks/FfiBoringssl/dart2/calloc.dart b/benchmarks/FfiBoringssl/dart2/calloc.dart
deleted file mode 100644
index c6be280..0000000
--- a/benchmarks/FfiBoringssl/dart2/calloc.dart
+++ /dev/null
@@ -1,111 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-// @dart=2.9
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/benchmarks/FfiCall/dart/FfiCall.dart b/benchmarks/FfiCall/dart/FfiCall.dart
index d33e120..ce48f50 100644
--- a/benchmarks/FfiCall/dart/FfiCall.dart
+++ b/benchmarks/FfiCall/dart/FfiCall.dart
@@ -13,7 +13,6 @@
 import 'package:ffi/ffi.dart';
 import 'package:benchmark_harness/benchmark_harness.dart';
 
-import 'calloc.dart';
 import 'dlopen_helper.dart';
 
 //
diff --git a/benchmarks/FfiCall/dart/calloc.dart b/benchmarks/FfiCall/dart/calloc.dart
deleted file mode 100644
index e17238a..0000000
--- a/benchmarks/FfiCall/dart/calloc.dart
+++ /dev/null
@@ -1,109 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int? alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/benchmarks/FfiCall/dart2/FfiCall.dart b/benchmarks/FfiCall/dart2/FfiCall.dart
index 3da29b4..3e6f297 100644
--- a/benchmarks/FfiCall/dart2/FfiCall.dart
+++ b/benchmarks/FfiCall/dart2/FfiCall.dart
@@ -15,7 +15,6 @@
 import 'package:ffi/ffi.dart';
 import 'package:benchmark_harness/benchmark_harness.dart';
 
-import 'calloc.dart';
 import 'dlopen_helper.dart';
 
 //
diff --git a/benchmarks/FfiCall/dart2/calloc.dart b/benchmarks/FfiCall/dart2/calloc.dart
deleted file mode 100644
index c6be280..0000000
--- a/benchmarks/FfiCall/dart2/calloc.dart
+++ /dev/null
@@ -1,111 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-// @dart=2.9
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/benchmarks/FfiMemory/dart/FfiMemory.dart b/benchmarks/FfiMemory/dart/FfiMemory.dart
index 423fa74..b776aa8 100644
--- a/benchmarks/FfiMemory/dart/FfiMemory.dart
+++ b/benchmarks/FfiMemory/dart/FfiMemory.dart
@@ -14,8 +14,6 @@
 import 'package:ffi/ffi.dart';
 import 'package:benchmark_harness/benchmark_harness.dart';
 
-import 'calloc.dart';
-
 //
 // Pointer store.
 //
diff --git a/benchmarks/FfiMemory/dart/calloc.dart b/benchmarks/FfiMemory/dart/calloc.dart
deleted file mode 100644
index e17238a..0000000
--- a/benchmarks/FfiMemory/dart/calloc.dart
+++ /dev/null
@@ -1,109 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int? alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/benchmarks/FfiMemory/dart2/FfiMemory.dart b/benchmarks/FfiMemory/dart2/FfiMemory.dart
index d8d41e2..5beff0a 100644
--- a/benchmarks/FfiMemory/dart2/FfiMemory.dart
+++ b/benchmarks/FfiMemory/dart2/FfiMemory.dart
@@ -16,8 +16,6 @@
 import 'package:ffi/ffi.dart';
 import 'package:benchmark_harness/benchmark_harness.dart';
 
-import 'calloc.dart';
-
 //
 // Pointer store.
 //
diff --git a/benchmarks/FfiMemory/dart2/calloc.dart b/benchmarks/FfiMemory/dart2/calloc.dart
deleted file mode 100644
index c6be280..0000000
--- a/benchmarks/FfiMemory/dart2/calloc.dart
+++ /dev/null
@@ -1,111 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-// @dart=2.9
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/benchmarks/FfiStruct/dart/FfiStruct.dart b/benchmarks/FfiStruct/dart/FfiStruct.dart
index a4a8f14..4fbc61c 100644
--- a/benchmarks/FfiStruct/dart/FfiStruct.dart
+++ b/benchmarks/FfiStruct/dart/FfiStruct.dart
@@ -12,8 +12,6 @@
 import 'package:ffi/ffi.dart';
 import 'package:benchmark_harness/benchmark_harness.dart';
 
-import 'calloc.dart';
-
 //
 // Struct field store (plus Pointer elementAt and load).
 //
diff --git a/benchmarks/FfiStruct/dart/calloc.dart b/benchmarks/FfiStruct/dart/calloc.dart
deleted file mode 100644
index e17238a..0000000
--- a/benchmarks/FfiStruct/dart/calloc.dart
+++ /dev/null
@@ -1,109 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int? alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/benchmarks/FfiStruct/dart2/FfiStruct.dart b/benchmarks/FfiStruct/dart2/FfiStruct.dart
index 6f4e17c..87f98de 100644
--- a/benchmarks/FfiStruct/dart2/FfiStruct.dart
+++ b/benchmarks/FfiStruct/dart2/FfiStruct.dart
@@ -14,8 +14,6 @@
 import 'package:ffi/ffi.dart';
 import 'package:benchmark_harness/benchmark_harness.dart';
 
-import 'calloc.dart';
-
 //
 // Struct field store (plus Pointer elementAt and load).
 //
diff --git a/benchmarks/FfiStruct/dart2/calloc.dart b/benchmarks/FfiStruct/dart2/calloc.dart
deleted file mode 100644
index c6be280..0000000
--- a/benchmarks/FfiStruct/dart2/calloc.dart
+++ /dev/null
@@ -1,111 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-// @dart=2.9
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/pkg/front_end/lib/src/fasta/dill/dill_loader.dart b/pkg/front_end/lib/src/fasta/dill/dill_loader.dart
index 8cbf077..6835a1b 100644
--- a/pkg/front_end/lib/src/fasta/dill/dill_loader.dart
+++ b/pkg/front_end/lib/src/fasta/dill/dill_loader.dart
@@ -95,11 +95,11 @@
   }
 
   void finalizeExports({bool suppressFinalizationErrors: false}) {
-    builders.forEach((Uri uri, LibraryBuilder builder) {
+    for (LibraryBuilder builder in builders.values) {
       DillLibraryBuilder library = builder;
       library.markAsReadyToFinalizeExports(
           suppressFinalizationErrors: suppressFinalizationErrors);
-    });
+    }
   }
 
   @override
diff --git a/pkg/front_end/lib/src/fasta/incremental_compiler.dart b/pkg/front_end/lib/src/fasta/incremental_compiler.dart
index cf844af..7beabe0 100644
--- a/pkg/front_end/lib/src/fasta/incremental_compiler.dart
+++ b/pkg/front_end/lib/src/fasta/incremental_compiler.dart
@@ -2137,6 +2137,10 @@
 
     for (Uri entryPoint in entryPoints) {
       LibraryBuilder parent = partUriToParent[entryPoint];
+      if (parent == null) continue;
+      // TODO(jensj): .contains on a list is O(n).
+      // It will only be done for each entry point that's a part though, i.e.
+      // most likely very rarely.
       if (reusedLibraries.contains(parent)) {
         result.registerLibraryUriForPartUsedAsEntryPoint(
             entryPoint, parent.importUri);
diff --git a/pkg/front_end/lib/src/fasta/kernel/constant_evaluator.dart b/pkg/front_end/lib/src/fasta/kernel/constant_evaluator.dart
index 9456de1..2f96cfa 100644
--- a/pkg/front_end/lib/src/fasta/kernel/constant_evaluator.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/constant_evaluator.dart
@@ -1449,17 +1449,17 @@
         instanceBuilder.setFieldValue(fieldRef.asField, constant);
       });
       if (error != null) return error;
-      node.unusedArguments.forEach((Expression value) {
-        if (error != null) return;
+      for (Expression value in node.unusedArguments) {
+        if (error != null) return error;
         Constant constant = _evaluateSubexpression(value);
         if (constant is AbortConstant) {
           error ??= constant;
-          return;
+          return error;
         }
         if (constant is UnevaluatedConstant) {
           instanceBuilder.unusedArguments.add(extract(constant));
         }
-      });
+      }
       if (error != null) return error;
       if (shouldBeUnevaluated) {
         return unevaluated(node, instanceBuilder.buildUnevaluatedInstance());
@@ -1485,7 +1485,7 @@
     //     - or the empty string (the default name of a library with no library
     //       name declaration).
 
-    const List<String> operatorNames = const <String>[
+    const Set<String> operatorNames = const <String>{
       '+',
       '-',
       '*',
@@ -1507,7 +1507,7 @@
       '[]',
       '[]=',
       'unary-'
-    ];
+    };
 
     if (name == null) return false;
     if (name == '') return true;
@@ -1554,7 +1554,7 @@
   static final RegExp publicIdentifierRegExp =
       new RegExp(r'^[a-zA-Z$][a-zA-Z0-9_$]*$');
 
-  static const List<String> nonUsableKeywords = const <String>[
+  static const Set<String> nonUsableKeywords = const <String>{
     'assert',
     'break',
     'case',
@@ -1587,7 +1587,7 @@
     'var',
     'while',
     'with',
-  ];
+  };
 
   bool isValidPublicIdentifier(String name) {
     return publicIdentifierRegExp.hasMatch(name) &&
@@ -3035,7 +3035,7 @@
     if (arguments.named.isEmpty) return const <String, Constant>{};
 
     final Map<String, Constant> named = {};
-    arguments.named.forEach((NamedExpression pair) {
+    for (NamedExpression pair in arguments.named) {
       if (_gotError != null) return null;
       Constant constant = _evaluateSubexpression(pair.value);
       if (constant is AbortConstant) {
@@ -3043,7 +3043,7 @@
         return null;
       }
       named[pair.name] = constant;
-    });
+    }
     if (_gotError != null) return null;
     return named;
   }
diff --git a/pkg/front_end/lib/src/fasta/kernel/kernel_target.dart b/pkg/front_end/lib/src/fasta/kernel/kernel_target.dart
index 513dac3..4e1b58b 100644
--- a/pkg/front_end/lib/src/fasta/kernel/kernel_target.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/kernel_target.dart
@@ -303,7 +303,7 @@
   /// Returns classes defined in libraries in [loader].
   List<SourceClassBuilder> collectMyClasses() {
     List<SourceClassBuilder> result = <SourceClassBuilder>[];
-    loader.builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in loader.builders.values) {
       if (library.loader == loader) {
         Iterator<Builder> iterator = library.iterator;
         while (iterator.moveNext()) {
@@ -313,7 +313,7 @@
           }
         }
       }
-    });
+    }
     return result;
   }
 
@@ -557,7 +557,7 @@
 
   void installDefaultSupertypes() {
     Class objectClass = this.objectClass;
-    loader.builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in loader.builders.values) {
       if (library.loader == loader) {
         Iterator<Builder> iterator = library.iterator;
         while (iterator.moveNext()) {
@@ -581,7 +581,7 @@
           }
         }
       }
-    });
+    }
     ticker.logMs("Installed Object as implicit superclass");
   }
 
@@ -1047,32 +1047,28 @@
         new Map<ConstructorBuilder, Set<FieldBuilder>>.identity();
     Set<FieldBuilder> initializedFields = null;
 
-    builder
-        .forEachDeclaredConstructor((String name, Builder constructorBuilder) {
-      if (constructorBuilder is ConstructorBuilder) {
-        if (constructorBuilder.isExternal) return;
-        // In case of duplicating constructors the earliest ones (those that
-        // declared towards the beginning of the file) come last in the list.
-        // To report errors on the first definition of a constructor, we need to
-        // iterate until that last element.
-        ConstructorBuilder earliest = constructorBuilder;
-        while (earliest.next != null) {
-          earliest = earliest.next;
-        }
+    builder.forEachDeclaredConstructor(
+        (String name, ConstructorBuilder constructorBuilder) {
+      if (constructorBuilder.isExternal) return;
+      // In case of duplicating constructors the earliest ones (those that
+      // declared towards the beginning of the file) come last in the list.
+      // To report errors on the first definition of a constructor, we need to
+      // iterate until that last element.
+      ConstructorBuilder earliest = constructorBuilder;
+      while (earliest.next != null) {
+        earliest = earliest.next;
+      }
 
-        bool isRedirecting = false;
-        for (Initializer initializer in earliest.constructor.initializers) {
-          if (initializer is RedirectingInitializer) {
-            isRedirecting = true;
-          }
+      bool isRedirecting = false;
+      for (Initializer initializer in earliest.constructor.initializers) {
+        if (initializer is RedirectingInitializer) {
+          isRedirecting = true;
         }
-        if (!isRedirecting) {
-          Set<FieldBuilder> fields =
-              earliest.takeInitializedFields() ?? const {};
-          constructorInitializedFields[earliest] = fields;
-          (initializedFields ??= new Set<FieldBuilder>.identity())
-              .addAll(fields);
-        }
+      }
+      if (!isRedirecting) {
+        Set<FieldBuilder> fields = earliest.takeInitializedFields() ?? const {};
+        constructorInitializedFields[earliest] = fields;
+        (initializedFields ??= new Set<FieldBuilder>.identity()).addAll(fields);
       }
     });
 
@@ -1339,7 +1335,9 @@
 
   /// Return `true` if the given [library] was built by this [KernelTarget]
   /// from sources, and not loaded from a [DillTarget].
-  bool isSourceLibrary(Library library) {
+  /// Note that this is meant for debugging etc and that it is slow, each
+  /// call takes O(# libraries).
+  bool isSourceLibraryForDebugging(Library library) {
     return loader.libraries.contains(library);
   }
 
diff --git a/pkg/front_end/lib/src/fasta/loader.dart b/pkg/front_end/lib/src/fasta/loader.dart
index 41da009..0652578 100644
--- a/pkg/front_end/lib/src/fasta/loader.dart
+++ b/pkg/front_end/lib/src/fasta/loader.dart
@@ -260,9 +260,9 @@
   void logSummary(Template<SummaryTemplate> template) {
     ticker.log((Duration elapsed, Duration sinceStart) {
       int libraryCount = 0;
-      builders.forEach((Uri uri, LibraryBuilder library) {
+      for (LibraryBuilder library in builders.values) {
         if (library.loader == this) libraryCount++;
-      });
+      }
       double ms = elapsed.inMicroseconds / Duration.microsecondsPerMillisecond;
       Message message = template.withArguments(
           libraryCount, byteCount, ms, byteCount / ms, ms / libraryCount);
diff --git a/pkg/front_end/lib/src/fasta/source/source_loader.dart b/pkg/front_end/lib/src/fasta/source/source_loader.dart
index bfcc018..153430d6 100644
--- a/pkg/front_end/lib/src/fasta/source/source_loader.dart
+++ b/pkg/front_end/lib/src/fasta/source/source_loader.dart
@@ -554,18 +554,18 @@
     }
     ticker.logMs("Resolved parts");
 
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         library.applyPatches();
       }
-    });
+    }
     ticker.logMs("Applied patches");
   }
 
   void computeLibraryScopes() {
     Set<LibraryBuilder> exporters = new Set<LibraryBuilder>();
     Set<LibraryBuilder> exportees = new Set<LibraryBuilder>();
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         SourceLibraryBuilder sourceLibrary = library;
         sourceLibrary.buildInitialScopes();
@@ -576,7 +576,7 @@
           exporters.add(exporter.exporter);
         }
       }
-    });
+    }
     Set<SourceLibraryBuilder> both = new Set<SourceLibraryBuilder>();
     for (LibraryBuilder exported in exportees) {
       if (exporters.contains(exported)) {
@@ -599,12 +599,12 @@
         }
       }
     } while (wasChanged);
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         SourceLibraryBuilder sourceLibrary = library;
         sourceLibrary.addImportsToScope();
       }
-    });
+    }
     for (LibraryBuilder exportee in exportees) {
       // TODO(ahe): Change how we track exporters. Currently, when a library
       // (exporter) exports another library (exportee) we add a reference to
@@ -642,94 +642,94 @@
 
   void resolveTypes() {
     int typeCount = 0;
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         SourceLibraryBuilder sourceLibrary = library;
         typeCount += sourceLibrary.resolveTypes();
       }
-    });
+    }
     ticker.logMs("Resolved $typeCount types");
   }
 
   void finishDeferredLoadTearoffs() {
     int count = 0;
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         count += library.finishDeferredLoadTearoffs();
       }
-    });
+    }
     ticker.logMs("Finished deferred load tearoffs $count");
   }
 
   void finishNoSuchMethodForwarders() {
     int count = 0;
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         count += library.finishForwarders();
       }
-    });
+    }
     ticker.logMs("Finished forwarders for $count procedures");
   }
 
   void resolveConstructors() {
     int count = 0;
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         count += library.resolveConstructors(null);
       }
-    });
+    }
     ticker.logMs("Resolved $count constructors");
   }
 
   void finishTypeVariables(ClassBuilder object, TypeBuilder dynamicType) {
     int count = 0;
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         count += library.finishTypeVariables(object, dynamicType);
       }
-    });
+    }
     ticker.logMs("Resolved $count type-variable bounds");
   }
 
   void computeVariances() {
     int count = 0;
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         count += library.computeVariances();
       }
-    });
+    }
     ticker.logMs("Computed variances of $count type variables");
   }
 
   void computeDefaultTypes(TypeBuilder dynamicType, TypeBuilder nullType,
       TypeBuilder bottomType, ClassBuilder objectClass) {
     int count = 0;
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         count += library.computeDefaultTypes(
             dynamicType, nullType, bottomType, objectClass);
       }
-    });
+    }
     ticker.logMs("Computed default types for $count type variables");
   }
 
   void finishNativeMethods() {
     int count = 0;
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         count += library.finishNativeMethods();
       }
-    });
+    }
     ticker.logMs("Finished $count native methods");
   }
 
   void finishPatchMethods() {
     int count = 0;
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         count += library.finishPatchMethods();
       }
-    });
+    }
     ticker.logMs("Finished $count patch methods");
   }
 
@@ -951,7 +951,7 @@
 
   /// Builds the core AST structure needed for the outline of the component.
   void buildComponent() {
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         SourceLibraryBuilder sourceLibrary = library;
         Library target = sourceLibrary.build(coreLibrary);
@@ -964,14 +964,14 @@
           libraries.add(target);
         }
       }
-    });
+    }
     ticker.logMs("Built component");
   }
 
   Component computeFullComponent() {
     Set<Library> libraries = new Set<Library>();
     List<Library> workList = <Library>[];
-    builders.forEach((Uri uri, LibraryBuilder libraryBuilder) {
+    for (LibraryBuilder libraryBuilder in builders.values) {
       if (!libraryBuilder.isPatch &&
           (libraryBuilder.loader == this ||
               libraryBuilder.importUri.scheme == "dart" ||
@@ -980,7 +980,7 @@
           workList.add(libraryBuilder.library);
         }
       }
-    });
+    }
     while (workList.isNotEmpty) {
       Library library = workList.removeLast();
       for (LibraryDependency dependency in library.dependencies) {
@@ -1056,14 +1056,14 @@
   }
 
   void checkTypes() {
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library is SourceLibraryBuilder) {
         if (library.loader == this) {
           library
               .checkTypesInOutline(typeInferenceEngine.typeSchemaEnvironment);
         }
       }
-    });
+    }
     ticker.logMs("Checked type arguments of supers against the bounds");
   }
 
@@ -1134,7 +1134,7 @@
   }
 
   void buildOutlineExpressions(CoreTypes coreTypes) {
-    builders.forEach((Uri uri, LibraryBuilder library) {
+    for (LibraryBuilder library in builders.values) {
       if (library.loader == this) {
         library.buildOutlineExpressions();
         Iterator<Builder> iterator = library.iterator;
@@ -1149,7 +1149,7 @@
           }
         }
       }
-    });
+    }
     ticker.logMs("Build outline expressions");
   }
 
@@ -1270,7 +1270,7 @@
   void checkMainMethods() {
     DartType listOfString;
 
-    builders.forEach((Uri uri, LibraryBuilder libraryBuilder) {
+    for (LibraryBuilder libraryBuilder in builders.values) {
       if (libraryBuilder.loader == this &&
           libraryBuilder.isNonNullableByDefault) {
         Builder mainBuilder =
@@ -1392,7 +1392,7 @@
           }
         }
       }
-    });
+    }
   }
 
   void releaseAncillaryResources() {
diff --git a/pkg/front_end/lib/src/fasta/type_inference/type_inference_engine.dart b/pkg/front_end/lib/src/fasta/type_inference/type_inference_engine.dart
index dc3235f..a95ec85 100644
--- a/pkg/front_end/lib/src/fasta/type_inference/type_inference_engine.dart
+++ b/pkg/front_end/lib/src/fasta/type_inference/type_inference_engine.dart
@@ -170,9 +170,9 @@
   void finishTopLevelInitializingFormals() {
     // Field types have all been inferred so we don't need to guard against
     // cyclic dependency.
-    toBeInferred.values.forEach((ConstructorBuilder builder) {
+    for (ConstructorBuilder builder in toBeInferred.values) {
       builder.inferFormalTypes();
-    });
+    }
     toBeInferred.clear();
   }
 
diff --git a/pkg/front_end/lib/src/kernel_generator_impl.dart b/pkg/front_end/lib/src/kernel_generator_impl.dart
index ac52474..b9737cc 100644
--- a/pkg/front_end/lib/src/kernel_generator_impl.dart
+++ b/pkg/front_end/lib/src/kernel_generator_impl.dart
@@ -110,7 +110,7 @@
       }
       if (options.debugDump) {
         printComponentText(summaryComponent,
-            libraryFilter: kernelTarget.isSourceLibrary);
+            libraryFilter: kernelTarget.isSourceLibraryForDebugging);
       }
 
       // Create the requested component ("truncating" or not).
@@ -164,7 +164,7 @@
       component = await kernelTarget.buildComponent(verify: options.verify);
       if (options.debugDump) {
         printComponentText(component,
-            libraryFilter: kernelTarget.isSourceLibrary);
+            libraryFilter: kernelTarget.isSourceLibraryForDebugging);
       }
       options.ticker.logMs("Generated component");
     }
diff --git a/pkg/front_end/test/spell_checking_list_code.txt b/pkg/front_end/test/spell_checking_list_code.txt
index 7fe58e0..d8d8bfd 100644
--- a/pkg/front_end/test/spell_checking_list_code.txt
+++ b/pkg/front_end/test/spell_checking_list_code.txt
@@ -912,6 +912,7 @@
 randomly
 ranges
 ranked
+rarely
 ratio
 rb
 rc
diff --git a/pkg/front_end/tool/_fasta/entry_points.dart b/pkg/front_end/tool/_fasta/entry_points.dart
index 9733184..e3c343a 100644
--- a/pkg/front_end/tool/_fasta/entry_points.dart
+++ b/pkg/front_end/tool/_fasta/entry_points.dart
@@ -333,7 +333,8 @@
     await dillTarget.buildOutlines();
     var outline = await kernelTarget.buildOutlines();
     if (c.options.debugDump && output != null) {
-      printComponentText(outline, libraryFilter: kernelTarget.isSourceLibrary);
+      printComponentText(outline,
+          libraryFilter: kernelTarget.isSourceLibraryForDebugging);
     }
     if (output != null) {
       if (omitPlatform) {
@@ -367,7 +368,7 @@
         await kernelTarget.buildComponent(verify: c.options.verify);
     if (c.options.debugDump) {
       printComponentText(component,
-          libraryFilter: kernelTarget.isSourceLibrary);
+          libraryFilter: kernelTarget.isSourceLibraryForDebugging);
     }
     if (omitPlatform) {
       component.computeCanonicalNames();
diff --git a/runtime/tests/vm/dart/isolates/dart_api_create_lightweight_isolate_test.dart b/runtime/tests/vm/dart/isolates/dart_api_create_lightweight_isolate_test.dart
index 34c3f23..be0d1ab 100644
--- a/runtime/tests/vm/dart/isolates/dart_api_create_lightweight_isolate_test.dart
+++ b/runtime/tests/vm/dart/isolates/dart_api_create_lightweight_isolate_test.dart
@@ -14,7 +14,6 @@
 import 'package:expect/expect.dart';
 import 'package:ffi/ffi.dart';
 
-import '../../../../../tests/ffi/calloc.dart';
 import '../../../../../tests/ffi/dylib_utils.dart';
 
 final bool isAOT = Platform.executable.contains('dart_precompiled_runtime');
diff --git a/runtime/tests/vm/dart/regress_41971_test.dart b/runtime/tests/vm/dart/regress_41971_test.dart
index 7979d0d..59212ad 100644
--- a/runtime/tests/vm/dart/regress_41971_test.dart
+++ b/runtime/tests/vm/dart/regress_41971_test.dart
@@ -11,8 +11,6 @@
 import 'package:expect/expect.dart';
 import 'package:ffi/ffi.dart';
 
-import '../../../../tests/ffi/calloc.dart';
-
 class X {
   int field;
   X(this.field);
diff --git a/runtime/tests/vm/dart/thread_priority_macos_test.dart b/runtime/tests/vm/dart/thread_priority_macos_test.dart
index 473c1ce..75e87d47 100644
--- a/runtime/tests/vm/dart/thread_priority_macos_test.dart
+++ b/runtime/tests/vm/dart/thread_priority_macos_test.dart
@@ -10,8 +10,6 @@
 import 'package:expect/expect.dart';
 import 'package:ffi/ffi.dart';
 
-import '../../../../tests/ffi/calloc.dart';
-
 // pthread_t pthread_self()
 typedef PthreadSelfFT = int Function();
 typedef PthreadSelfNFT = IntPtr Function();
diff --git a/runtime/tests/vm/dart_2/isolates/dart_api_create_lightweight_isolate_test.dart b/runtime/tests/vm/dart_2/isolates/dart_api_create_lightweight_isolate_test.dart
index 9c1a5c2..73366bb 100644
--- a/runtime/tests/vm/dart_2/isolates/dart_api_create_lightweight_isolate_test.dart
+++ b/runtime/tests/vm/dart_2/isolates/dart_api_create_lightweight_isolate_test.dart
@@ -14,7 +14,6 @@
 import 'package:expect/expect.dart';
 import 'package:ffi/ffi.dart';
 
-import '../../../../../tests/ffi/calloc.dart';
 import '../../../../../tests/ffi/dylib_utils.dart';
 
 final bool isAOT = Platform.executable.contains('dart_precompiled_runtime');
diff --git a/runtime/tests/vm/dart_2/regress_41971_test.dart b/runtime/tests/vm/dart_2/regress_41971_test.dart
index 7979d0d..59212ad 100644
--- a/runtime/tests/vm/dart_2/regress_41971_test.dart
+++ b/runtime/tests/vm/dart_2/regress_41971_test.dart
@@ -11,8 +11,6 @@
 import 'package:expect/expect.dart';
 import 'package:ffi/ffi.dart';
 
-import '../../../../tests/ffi/calloc.dart';
-
 class X {
   int field;
   X(this.field);
diff --git a/runtime/tests/vm/dart_2/thread_priority_macos_test.dart b/runtime/tests/vm/dart_2/thread_priority_macos_test.dart
index fdce726..f1574cf 100644
--- a/runtime/tests/vm/dart_2/thread_priority_macos_test.dart
+++ b/runtime/tests/vm/dart_2/thread_priority_macos_test.dart
@@ -10,8 +10,6 @@
 import 'package:expect/expect.dart';
 import 'package:ffi/ffi.dart';
 
-import '../../../../tests/ffi/calloc.dart';
-
 // pthread_t pthread_self()
 typedef PthreadSelfFT = int Function();
 typedef PthreadSelfNFT = IntPtr Function();
diff --git a/runtime/vm/compiler/ffi/native_calling_convention.cc b/runtime/vm/compiler/ffi/native_calling_convention.cc
index 86b2eba..a0c1f30 100644
--- a/runtime/vm/compiler/ffi/native_calling_convention.cc
+++ b/runtime/vm/compiler/ffi/native_calling_convention.cc
@@ -158,8 +158,8 @@
             zone_, required_regs + required_xmm_regs);
         for (intptr_t offset = 0; offset < size;
              offset += compiler::target::kWordSize) {
-          if (payload_type.ContainsOnlyFloats(
-                  offset, Utils::Minimum<intptr_t>(size - offset, 8))) {
+          if (payload_type.ContainsOnlyFloats(Range::StartAndEnd(
+                  offset, Utils::Minimum<intptr_t>(size, offset + 8)))) {
             const intptr_t reg_index = FirstFreeFpuRegisterIndex(kQuadFpuReg);
             AllocateFpuRegisterAtIndex(kQuadFpuReg, reg_index);
             const auto& type = *new (zone_) NativePrimitiveType(kDouble);
@@ -527,8 +527,8 @@
     const auto& double_type = *new (zone) NativePrimitiveType(kDouble);
     const auto& int64_type = *new (zone) NativePrimitiveType(kInt64);
 
-    const bool first_half_in_xmm =
-        payload_type.ContainsOnlyFloats(0, Utils::Minimum<intptr_t>(size, 8));
+    const bool first_half_in_xmm = payload_type.ContainsOnlyFloats(
+        Range::StartAndEnd(0, Utils::Minimum<intptr_t>(size, 8)));
     if (first_half_in_xmm) {
       multiple_locations.Add(new (zone) NativeFpuRegistersLocation(
           double_type, double_type, kQuadFpuReg,
@@ -541,7 +541,7 @@
     }
     if (size > 8) {
       const bool second_half_in_xmm = payload_type.ContainsOnlyFloats(
-          8, Utils::Minimum<intptr_t>(size - 8, 8));
+          Range::StartAndEnd(8, Utils::Minimum<intptr_t>(size, 16)));
       if (second_half_in_xmm) {
         const FpuRegister reg = used_xmm_regs == 0
                                     ? CallingConventions::kReturnFpuReg
diff --git a/runtime/vm/compiler/ffi/native_calling_convention_test.cc b/runtime/vm/compiler/ffi/native_calling_convention_test.cc
index 8b27760..82db265 100644
--- a/runtime/vm/compiler/ffi/native_calling_convention_test.cc
+++ b/runtime/vm/compiler/ffi/native_calling_convention_test.cc
@@ -159,6 +159,50 @@
   RunSignatureTest(Z, "struct16bytesHomogenousx10", arguments, struct_type);
 }
 
+// Test with homogenous struct (2).
+//
+// This time with nested structs and inline arrays.
+//
+// See the *.expect in ./unit_tests for this behavior.
+UNIT_TEST_CASE_WITH_ZONE(NativeCallingConvention_struct16bytesHomogenousx10_2) {
+  const auto& float_type = *new (Z) NativePrimitiveType(kFloat);
+  const auto& int8type = *new (Z) NativePrimitiveType(kInt8);
+
+  const auto& float_1_array_type = *new (Z) NativeArrayType(float_type, 1);
+
+  const auto& float_2_array_type = *new (Z) NativeArrayType(float_type, 2);
+  auto& full_float_member_types = *new (Z) NativeTypes(Z, 1);
+  full_float_member_types.Add(&float_2_array_type);
+  const auto& float_array_struct_type =
+      NativeCompoundType::FromNativeTypes(Z, full_float_member_types);
+
+  auto& member_types = *new (Z) NativeTypes(Z, 3);
+  member_types.Add(&float_1_array_type);
+  member_types.Add(&float_array_struct_type);
+  member_types.Add(&float_type);
+  const auto& struct_type =
+      NativeCompoundType::FromNativeTypes(Z, member_types);
+
+  auto& arguments = *new (Z) NativeTypes(Z, 13);
+  arguments.Add(&struct_type);
+  arguments.Add(&float_type);  // Claim a single FPU register.
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&float_type);   // Check float register back filling, if any.
+  arguments.Add(&int8type);     // Check integer register back filling, if any.
+  arguments.Add(&struct_type);  // Check stack alignment of struct.
+
+  // Identical expectation files as previous test, struct contains the same
+  // members, but nested in arrays and nested structs.
+  RunSignatureTest(Z, "struct16bytesHomogenousx10", arguments, struct_type);
+}
+
 // A fairly big struct.
 //
 // On arm, split up in 8-byte chunks. The first chunk goes into two registers,
@@ -269,6 +313,65 @@
 
   RunSignatureTest(Z, "struct16bytesMixedx10_2", arguments, struct_type);
 }
+
+// On x64 non-Windows a struct can be spread over an FPU and int register.
+//
+// This behavior also happens with nested structs and inline arrays.
+//
+// typedef struct  {
+//   int32_t a0;
+//   float a1;
+// } HalfFloat;
+//
+// typedef struct  {
+//   float a1[1];
+// } FullFloat;
+//
+// typedef struct  {
+//   int32_t a0;
+//   HalfFloat a1;
+//   FullFloat a2;
+// } HalfFloat2;
+//
+// See the *.expect in ./unit_tests for this behavior.
+UNIT_TEST_CASE_WITH_ZONE(NativeCallingConvention_struct16bytesMixedx10_3) {
+  const auto& float_type = *new (Z) NativePrimitiveType(kFloat);
+  const auto& int32_type = *new (Z) NativePrimitiveType(kInt32);
+
+  auto& half_float_member_types = *new (Z) NativeTypes(Z, 2);
+  half_float_member_types.Add(&int32_type);
+  half_float_member_types.Add(&float_type);
+  const auto& half_float_type =
+      NativeCompoundType::FromNativeTypes(Z, half_float_member_types);
+
+  const auto& float_array_type = *new (Z) NativeArrayType(float_type, 1);
+  auto& full_float_member_types = *new (Z) NativeTypes(Z, 1);
+  full_float_member_types.Add(&float_array_type);
+  const auto& full_float_type =
+      NativeCompoundType::FromNativeTypes(Z, full_float_member_types);
+
+  auto& member_types = *new (Z) NativeTypes(Z, 3);
+  member_types.Add(&int32_type);
+  member_types.Add(&half_float_type);
+  member_types.Add(&full_float_type);
+  const auto& struct_type =
+      NativeCompoundType::FromNativeTypes(Z, member_types);
+
+  auto& arguments = *new (Z) NativeTypes(Z, 11);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);  // Integer registers exhausted, on stack.
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&struct_type);
+  arguments.Add(&float_type);  // Use remaining FPU register.
+
+  RunSignatureTest(Z, "struct16bytesMixedx10_3", arguments, struct_type);
+}
 #endif  // defined(TARGET_ARCH_X64)
 
 // On ia32 Windows a struct can be returned in registers, on non-Windows not.
diff --git a/runtime/vm/compiler/ffi/native_type.cc b/runtime/vm/compiler/ffi/native_type.cc
index 837c17f..7e1ade5 100644
--- a/runtime/vm/compiler/ffi/native_type.cc
+++ b/runtime/vm/compiler/ffi/native_type.cc
@@ -46,6 +46,11 @@
   return static_cast<const NativePrimitiveType&>(*this);
 }
 
+const NativeArrayType& NativeType::AsArray() const {
+  ASSERT(IsArray());
+  return static_cast<const NativeArrayType&>(*this);
+}
+
 const NativeCompoundType& NativeType::AsCompound() const {
   ASSERT(IsCompound());
   return static_cast<const NativeCompoundType&>(*this);
@@ -256,6 +261,14 @@
   return other.AsPrimitive().representation_ == representation_;
 }
 
+bool NativeArrayType::Equals(const NativeType& other) const {
+  if (!other.IsArray()) {
+    return false;
+  }
+  return other.AsArray().length_ == length_ &&
+         other.AsArray().element_type_.Equals(element_type_);
+}
+
 bool NativeCompoundType::Equals(const NativeType& other) const {
   if (!other.IsCompound()) {
     return false;
@@ -462,6 +475,16 @@
   return textBuffer.buffer();
 }
 
+void NativeArrayType::PrintTo(BaseTextBuffer* f,
+                              bool multi_line,
+                              bool verbose) const {
+  f->AddString("Array(");
+  f->Printf("element type: ");
+  element_type_.PrintTo(f, /*multi_line*/ false, verbose);
+  f->Printf(", length: %" Pd "", length_);
+  f->AddString(")");
+}
+
 void NativeCompoundType::PrintTo(BaseTextBuffer* f,
                                  bool multi_line,
                                  bool verbose) const {
@@ -518,6 +541,10 @@
   return 1;
 }
 
+intptr_t NativeArrayType::NumPrimitiveMembersRecursive() const {
+  return element_type_.NumPrimitiveMembersRecursive() * length_;
+}
+
 intptr_t NativeCompoundType::NumPrimitiveMembersRecursive() const {
   intptr_t count = 0;
   for (intptr_t i = 0; i < members_.length(); i++) {
@@ -530,6 +557,10 @@
   return *this;
 }
 
+const NativePrimitiveType& NativeArrayType::FirstPrimitiveMember() const {
+  return element_type_.FirstPrimitiveMember();
+}
+
 const NativePrimitiveType& NativeCompoundType::FirstPrimitiveMember() const {
   ASSERT(NumPrimitiveMembersRecursive() >= 1);
   for (intptr_t i = 0; i < members().length(); i++) {
@@ -540,30 +571,77 @@
   UNREACHABLE();
 }
 
-bool NativeCompoundType::ContainsOnlyFloats(intptr_t offset_in_bytes,
-                                            intptr_t size_in_bytes) const {
-  ASSERT(size_in_bytes >= 0);
-  const intptr_t first_byte = offset_in_bytes;
-  const intptr_t last_byte = offset_in_bytes + size_in_bytes - 1;
+#if !defined(DART_PRECOMPILED_RUNTIME)
+bool NativePrimitiveType::ContainsOnlyFloats(Range range) const {
+  const auto this_range = Range::StartAndEnd(0, SizeInBytes());
+  ASSERT(this_range.Contains(range));
+
+  return IsFloat();
+}
+
+bool NativeArrayType::ContainsOnlyFloats(Range range) const {
+  const auto this_range = Range::StartAndEnd(0, SizeInBytes());
+  ASSERT(this_range.Contains(range));
+
+  const intptr_t element_size_in_bytes = element_type_.SizeInBytes();
+
+  // Assess how many elements are (partially) covered by the range.
+  const intptr_t first_element_start = range.start() / element_size_in_bytes;
+  const intptr_t last_element_index =
+      range.end_inclusive() / element_size_in_bytes;
+  const intptr_t num_elements = last_element_index - first_element_start + 1;
+  ASSERT(num_elements >= 1);
+
+  if (num_elements > 2) {
+    // At least one full element covered.
+    return element_type_.ContainsOnlyFloats(
+        Range::StartAndLength(0, element_size_in_bytes));
+  }
+
+  // Check first element, which falls (partially) in range.
+  const intptr_t first_start = first_element_start * element_size_in_bytes;
+  const auto first_range =
+      Range::StartAndLength(first_start, element_size_in_bytes);
+  const auto first_range_clipped = range.Intersect(first_range);
+  const auto range_in_first = first_range_clipped.Translate(-first_start);
+  if (!element_type_.ContainsOnlyFloats(range_in_first)) {
+    // First element contains not only floats in specified range.
+    return false;
+  }
+
+  if (num_elements == 2) {
+    // Check the second (and last) element, which falls (partially) in range.
+    const intptr_t second_element_index = first_element_start + 1;
+    const intptr_t second_start = second_element_index * element_size_in_bytes;
+    const auto second_range =
+        Range::StartAndLength(second_start, element_size_in_bytes);
+    const auto second_range_clipped = range.Intersect(second_range);
+    const auto range_in_second = second_range_clipped.Translate(-second_start);
+    return element_type_.ContainsOnlyFloats(range_in_second);
+  }
+
+  return true;
+}
+
+bool NativeCompoundType::ContainsOnlyFloats(Range range) const {
+  const auto this_range = Range::StartAndEnd(0, SizeInBytes());
+  ASSERT(this_range.Contains(range));
+
   for (intptr_t i = 0; i < members_.length(); i++) {
-    const intptr_t member_first_byte = member_offsets_[i];
-    const intptr_t member_last_byte =
-        member_first_byte + members_[i]->SizeInBytes() - 1;
-    if ((first_byte <= member_first_byte && member_first_byte <= last_byte) ||
-        (first_byte <= member_last_byte && member_last_byte <= last_byte)) {
-      if (members_[i]->IsPrimitive() && !members_[i]->IsFloat()) {
+    const auto& member = *members_[i];
+    const intptr_t member_offset = member_offsets_[i];
+    const intptr_t member_size = member.SizeInBytes();
+    const auto member_range = Range::StartAndLength(member_offset, member_size);
+    if (range.Overlaps(member_range)) {
+      const auto member_range_clipped = member_range.Intersect(range);
+      const auto range_in_member =
+          member_range_clipped.Translate(-member_offset);
+      if (!member.ContainsOnlyFloats(range_in_member)) {
+        // Member contains not only floats in specified range.
         return false;
       }
-      if (members_[i]->IsCompound()) {
-        const auto& nested = members_[i]->AsCompound();
-        const bool nested_only_floats = nested.ContainsOnlyFloats(
-            offset_in_bytes - member_first_byte, size_in_bytes);
-        if (!nested_only_floats) {
-          return false;
-        }
-      }
     }
-    if (member_first_byte > last_byte) {
+    if (member_range.After(range)) {
       // None of the remaining members fits the range.
       break;
     }
@@ -574,13 +652,14 @@
 intptr_t NativeCompoundType::NumberOfWordSizeChunksOnlyFloat() const {
   // O(n^2) implementation, but only invoked for small structs.
   ASSERT(SizeInBytes() <= 16);
+  const auto this_range = Range::StartAndEnd(0, SizeInBytes());
   const intptr_t size = SizeInBytes();
   intptr_t float_only_chunks = 0;
   for (intptr_t offset = 0; offset < size;
        offset += compiler::target::kWordSize) {
-    if (ContainsOnlyFloats(
-            offset, Utils::Minimum<intptr_t>(size - offset,
-                                             compiler::target::kWordSize))) {
+    const auto chunk_range =
+        Range::StartAndLength(offset, compiler::target::kWordSize);
+    if (ContainsOnlyFloats(chunk_range.Intersect(this_range))) {
       float_only_chunks++;
     }
   }
@@ -593,19 +672,22 @@
       compiler::target::kWordSize;
   return total_chunks - NumberOfWordSizeChunksOnlyFloat();
 }
+#endif  // !defined(DART_PRECOMPILED_RUNTIME)
 
 static void ContainsHomogenuousFloatsRecursive(const NativeTypes& types,
                                                bool* only_float,
                                                bool* only_double) {
   for (intptr_t i = 0; i < types.length(); i++) {
-    const auto& member_type = types.At(i);
-    if (member_type->IsPrimitive()) {
-      PrimitiveType type = member_type->AsPrimitive().representation();
+    const auto& type = *types.At(i);
+    const auto& member_type =
+        type.IsArray() ? type.AsArray().element_type() : type;
+    if (member_type.IsPrimitive()) {
+      PrimitiveType type = member_type.AsPrimitive().representation();
       *only_float = *only_float && (type == kFloat);
       *only_double = *only_double && (type == kDouble);
     }
-    if (member_type->IsCompound()) {
-      ContainsHomogenuousFloatsRecursive(member_type->AsCompound().members(),
+    if (member_type.IsCompound()) {
+      ContainsHomogenuousFloatsRecursive(member_type.AsCompound().members(),
                                          only_float, only_double);
     }
   }
diff --git a/runtime/vm/compiler/ffi/native_type.h b/runtime/vm/compiler/ffi/native_type.h
index 73d6915..9b3df3f 100644
--- a/runtime/vm/compiler/ffi/native_type.h
+++ b/runtime/vm/compiler/ffi/native_type.h
@@ -10,6 +10,9 @@
 #include "vm/allocation.h"
 #include "vm/growable_array.h"
 
+#if !defined(DART_PRECOMPILED_RUNTIME)
+#include "vm/compiler/ffi/range.h"
+#endif
 #if !defined(DART_PRECOMPILED_RUNTIME) && !defined(FFI_UNIT_TESTS)
 #include "vm/compiler/backend/locations.h"
 #endif
@@ -26,6 +29,7 @@
 namespace ffi {
 
 class NativePrimitiveType;
+class NativeArrayType;
 class NativeCompoundType;
 
 // NativeTypes are the types used in calling convention specifications:
@@ -64,6 +68,8 @@
 
   virtual bool IsPrimitive() const { return false; }
   const NativePrimitiveType& AsPrimitive() const;
+  virtual bool IsArray() const { return false; }
+  const NativeArrayType& AsArray() const;
   virtual bool IsCompound() const { return false; }
   const NativeCompoundType& AsCompound() const;
 
@@ -84,6 +90,13 @@
   // The alignment in bytes of this representation as member of a composite.
   virtual intptr_t AlignmentInBytesField() const = 0;
 
+#if !defined(DART_PRECOMPILED_RUNTIME)
+  // Returns true iff a range within this type contains only floats.
+  //
+  // Useful for determining whether struct is passed in FP registers on x64.
+  virtual bool ContainsOnlyFloats(Range range) const = 0;
+#endif  // !defined(DART_PRECOMPILED_RUNTIME)
+
 #if !defined(DART_PRECOMPILED_RUNTIME) && !defined(FFI_UNIT_TESTS)
   // NativeTypes which are available as unboxed Representations.
   virtual bool IsExpressibleAsRepresentation() const { return false; }
@@ -117,10 +130,8 @@
   const char* ToCString() const;
 #endif
 
-  virtual intptr_t NumPrimitiveMembersRecursive() const { UNREACHABLE(); }
-  virtual const NativePrimitiveType& FirstPrimitiveMember() const {
-    UNREACHABLE();
-  }
+  virtual intptr_t NumPrimitiveMembersRecursive() const = 0;
+  virtual const NativePrimitiveType& FirstPrimitiveMember() const = 0;
 
   virtual ~NativeType() {}
 
@@ -170,6 +181,10 @@
   virtual intptr_t AlignmentInBytesStack() const;
   virtual intptr_t AlignmentInBytesField() const;
 
+#if !defined(DART_PRECOMPILED_RUNTIME)
+  virtual bool ContainsOnlyFloats(Range range) const;
+#endif  // !defined(DART_PRECOMPILED_RUNTIME)
+
 #if !defined(DART_PRECOMPILED_RUNTIME) && !defined(FFI_UNIT_TESTS)
   virtual bool IsExpressibleAsRepresentation() const;
   virtual Representation AsRepresentation() const;
@@ -191,12 +206,53 @@
   const PrimitiveType representation_;
 };
 
+// Fixed-length arrays.
+class NativeArrayType : public NativeType {
+ public:
+  NativeArrayType(const NativeType& element_type, intptr_t length)
+      : element_type_(element_type), length_(length) {
+    ASSERT(!element_type.IsArray());
+    ASSERT(length > 0);
+  }
+
+  const NativeType& element_type() const { return element_type_; }
+  intptr_t length() const { return length_; }
+
+  virtual bool IsArray() const { return true; }
+
+  virtual intptr_t SizeInBytes() const {
+    return element_type_.SizeInBytes() * length_;
+  }
+  virtual intptr_t AlignmentInBytesField() const {
+    return element_type_.AlignmentInBytesField();
+  }
+  virtual intptr_t AlignmentInBytesStack() const {
+    return element_type_.AlignmentInBytesStack();
+  }
+
+#if !defined(DART_PRECOMPILED_RUNTIME)
+  virtual bool ContainsOnlyFloats(Range range) const;
+#endif  // !defined(DART_PRECOMPILED_RUNTIME)
+
+  virtual bool Equals(const NativeType& other) const;
+
+  virtual void PrintTo(BaseTextBuffer* f,
+                       bool multi_line = false,
+                       bool verbose = true) const;
+
+  virtual intptr_t NumPrimitiveMembersRecursive() const;
+  virtual const NativePrimitiveType& FirstPrimitiveMember() const;
+
+ private:
+  const NativeType& element_type_;
+  const intptr_t length_;
+};
+
 using NativeTypes = ZoneGrowableArray<const NativeType*>;
 
 // Struct
 //
 // TODO(dartbug.com/38491): Support unions.
-// TODO(dartbug.com/35763): Support inline fixed-length arrays.
 class NativeCompoundType : public NativeType {
  public:
   static NativeCompoundType& FromNativeTypes(Zone* zone,
@@ -219,11 +275,8 @@
                        bool multi_line = false,
                        bool verbose = true) const;
 
-  // Whether a range within a struct contains only floats.
-  //
-  // Useful for determining whether struct is passed in FP registers on x64.
-  bool ContainsOnlyFloats(intptr_t offset_in_bytes,
-                          intptr_t size_in_bytes) const;
+#if !defined(DART_PRECOMPILED_RUNTIME)
+  virtual bool ContainsOnlyFloats(Range range) const;
 
   // Returns how many word-sized chuncks _only_ contain floats.
   //
@@ -234,6 +287,7 @@
   //
   // Useful for determining whether struct is passed in FP registers on x64.
   intptr_t NumberOfWordSizeChunksNotOnlyFloat() const;
+#endif  // !defined(DART_PRECOMPILED_RUNTIME)
 
   // Whether this type has only same-size floating point members.
   //
diff --git a/runtime/vm/compiler/ffi/native_type_test.cc b/runtime/vm/compiler/ffi/native_type_test.cc
index 66fa987..d71e0e3 100644
--- a/runtime/vm/compiler/ffi/native_type_test.cc
+++ b/runtime/vm/compiler/ffi/native_type_test.cc
@@ -70,7 +70,7 @@
   const auto& struct_type = RunStructTest(Z, "struct_int8x10", members);
 
   EXPECT(!struct_type.ContainsHomogenuousFloats());
-  EXPECT(!struct_type.ContainsOnlyFloats(0, 8));
+  EXPECT(!struct_type.ContainsOnlyFloats(Range::StartAndEnd(0, 8)));
   EXPECT_EQ(0, struct_type.NumberOfWordSizeChunksOnlyFloat());
   EXPECT_EQ(
       Utils::RoundUp(struct_type.SizeInBytes(), compiler::target::kWordSize) /
@@ -97,8 +97,8 @@
 
   // On x64, 8-byte parts of the chunks contain only floats and will be passed
   // in FPU registers.
-  EXPECT(struct_type.ContainsOnlyFloats(0, 8));
-  EXPECT(struct_type.ContainsOnlyFloats(8, 8));
+  EXPECT(struct_type.ContainsOnlyFloats(Range::StartAndEnd(0, 8)));
+  EXPECT(struct_type.ContainsOnlyFloats(Range::StartAndEnd(8, 16)));
   EXPECT_EQ(struct_type.SizeInBytes() / compiler::target::kWordSize,
             struct_type.NumberOfWordSizeChunksOnlyFloat());
   EXPECT_EQ(0, struct_type.NumberOfWordSizeChunksNotOnlyFloat());
@@ -153,6 +153,49 @@
   RunStructTest(Z, "struct_VeryLargeStruct", members);
 }
 
+UNIT_TEST_CASE_WITH_ZONE(NativeCompoundType_int8array) {
+  const auto& int8type = *new (Z) NativePrimitiveType(kInt8);
+  const auto& array_type = *new (Z) NativeArrayType(int8type, 8);
+
+  auto& members = *new (Z) NativeTypes(Z, 1);
+  members.Add(&array_type);
+
+  const auto& struct_type = RunStructTest(Z, "struct_int8array", members);
+
+  EXPECT_EQ(8, struct_type.SizeInBytes());
+  EXPECT(!struct_type.ContainsHomogenuousFloats());
+  EXPECT(!struct_type.ContainsOnlyFloats(Range::StartAndEnd(0, 8)));
+  EXPECT_EQ(0, struct_type.NumberOfWordSizeChunksOnlyFloat());
+  EXPECT_EQ(
+      Utils::RoundUp(struct_type.SizeInBytes(), compiler::target::kWordSize) /
+          compiler::target::kWordSize,
+      struct_type.NumberOfWordSizeChunksNotOnlyFloat());
+}
+
+UNIT_TEST_CASE_WITH_ZONE(NativeCompoundType_floatarray) {
+  const auto& float_type = *new (Z) NativePrimitiveType(kFloat);
+
+  const auto& inner_array_type = *new (Z) NativeArrayType(float_type, 2);
+
+  auto& inner_struct_members = *new (Z) NativeTypes(Z, 1);
+  inner_struct_members.Add(&inner_array_type);
+  const auto& inner_struct =
+      NativeCompoundType::FromNativeTypes(Z, inner_struct_members);
+
+  const auto& array_type = *new (Z) NativeArrayType(inner_struct, 2);
+
+  auto& members = *new (Z) NativeTypes(Z, 1);
+  members.Add(&array_type);
+
+  const auto& struct_type = RunStructTest(Z, "struct_floatarray", members);
+
+  EXPECT_EQ(16, struct_type.SizeInBytes());
+  EXPECT(struct_type.ContainsHomogenuousFloats());
+  EXPECT(struct_type.ContainsOnlyFloats(Range::StartAndEnd(0, 8)));
+  EXPECT_EQ(16 / compiler::target::kWordSize,
+            struct_type.NumberOfWordSizeChunksOnlyFloat());
+}
+
 }  // namespace ffi
 }  // namespace compiler
 }  // namespace dart
diff --git a/runtime/vm/compiler/ffi/range.h b/runtime/vm/compiler/ffi/range.h
new file mode 100644
index 0000000..0848875
--- /dev/null
+++ b/runtime/vm/compiler/ffi/range.h
@@ -0,0 +1,103 @@
+// Copyright (c) 2021, 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 RUNTIME_VM_COMPILER_FFI_RANGE_H_
+#define RUNTIME_VM_COMPILER_FFI_RANGE_H_
+
+#include "platform/assert.h"
+#include "platform/utils.h"
+#include "vm/allocation.h"
+
+namespace dart {
+
+namespace compiler {
+
+namespace ffi {
+
+// A non-empty range.
+//
+// Ranges are positive and non-empty.
+//
+// The end is exclusive.
+class Range : public ValueObject {
+ public:
+  // Constructs a Range from start (inclusive) and length.
+  //
+  // The resulting range is `[start_inclusive, start_inclusive + length)`.
+  static Range StartAndLength(intptr_t start_inclusive, intptr_t length) {
+    return Range(start_inclusive, start_inclusive + length);
+  }
+
+  // Constructs a Range from start (inclusive) and end (exclusive).
+  //
+  // The resulting range is `[start_inclusive, end_exclusive)`.
+  static Range StartAndEnd(intptr_t start_inclusive, intptr_t end_exclusive) {
+    return Range(start_inclusive, end_exclusive);
+  }
+
+  Range(const Range& other)
+      : start_(other.start_), end_exclusive_(other.end_exclusive_) {}
+
+  intptr_t start() const { return start_; }
+  intptr_t end_exclusive() const { return end_exclusive_; }
+  intptr_t end_inclusive() const { return end_exclusive_ - 1; }
+
+  intptr_t Length() const { return end_exclusive_ - start_; }
+
+  // Returs true iff number is in this range.
+  bool Contains(intptr_t number) const {
+    return start_ <= number && number < end_exclusive_;
+  }
+
+  // Returns true iff [this] contains [other] completely.
+  bool Contains(const Range& other) const {
+    return Contains(other.start_) && Contains(other.end_inclusive());
+  }
+
+  // Returns true iff [this] is completey after [other].
+  bool After(const Range& other) const {
+    return other.end_exclusive_ <= start_;
+  }
+
+  // Returns true iff [this] contains some numbers of [other].
+  bool Overlaps(const Range& other) const {
+    return !this->After(other) && !other.After(*this);
+  }
+
+  // Returns the intersection of [this] with [other].
+  //
+  // Requires [this] and [other] to overlap.
+  const Range Intersect(const Range& other) const {
+    ASSERT(Overlaps(other));
+    return Range(Utils::Maximum(start_, other.start_),
+                 Utils::Minimum(end_exclusive_, other.end_exclusive_));
+  }
+
+  // Returns a range moved by [delta].
+  //
+  // `this.start() - delta` must be positive.
+  const Range Translate(intptr_t delta) const {
+    return Range(start_ + delta, end_exclusive_ + delta);
+  }
+
+ private:
+  Range(intptr_t start_inclusive, intptr_t end_exclusive)
+      : start_(start_inclusive), end_exclusive_(end_exclusive) {
+    if (!(start_ >= 0 && end_exclusive_ > start_)) {
+      ASSERT(start_ >= 0);
+      ASSERT(end_exclusive_ > start_);
+    }
+  }
+
+  const intptr_t start_;
+  const intptr_t end_exclusive_;
+};
+
+}  // namespace ffi
+
+}  // namespace compiler
+
+}  // namespace dart
+
+#endif  // RUNTIME_VM_COMPILER_FFI_RANGE_H_
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_ios.expect b/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_ios.expect
new file mode 100644
index 0000000..a9ed4cd
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_ios.expect
@@ -0,0 +1,13 @@
+M(rdi int64, xmm0 double) Compound(size: 16)
+M(rsi int64, xmm1 double) Compound(size: 16)
+M(rdx int64, xmm2 double) Compound(size: 16)
+M(rcx int64, xmm3 double) Compound(size: 16)
+M(r8 int64, xmm4 double) Compound(size: 16)
+M(r9 int64, xmm5 double) Compound(size: 16)
+S+0 Compound(size: 16)
+S+16 Compound(size: 16)
+S+32 Compound(size: 16)
+S+48 Compound(size: 16)
+xmm6 float
+=>
+M(rax int64, xmm0 double) Compound(size: 16)
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_linux.expect b/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_linux.expect
new file mode 100644
index 0000000..a9ed4cd
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_linux.expect
@@ -0,0 +1,13 @@
+M(rdi int64, xmm0 double) Compound(size: 16)
+M(rsi int64, xmm1 double) Compound(size: 16)
+M(rdx int64, xmm2 double) Compound(size: 16)
+M(rcx int64, xmm3 double) Compound(size: 16)
+M(r8 int64, xmm4 double) Compound(size: 16)
+M(r9 int64, xmm5 double) Compound(size: 16)
+S+0 Compound(size: 16)
+S+16 Compound(size: 16)
+S+32 Compound(size: 16)
+S+48 Compound(size: 16)
+xmm6 float
+=>
+M(rax int64, xmm0 double) Compound(size: 16)
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_macos.expect b/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_macos.expect
new file mode 100644
index 0000000..a9ed4cd
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_macos.expect
@@ -0,0 +1,13 @@
+M(rdi int64, xmm0 double) Compound(size: 16)
+M(rsi int64, xmm1 double) Compound(size: 16)
+M(rdx int64, xmm2 double) Compound(size: 16)
+M(rcx int64, xmm3 double) Compound(size: 16)
+M(r8 int64, xmm4 double) Compound(size: 16)
+M(r9 int64, xmm5 double) Compound(size: 16)
+S+0 Compound(size: 16)
+S+16 Compound(size: 16)
+S+32 Compound(size: 16)
+S+48 Compound(size: 16)
+xmm6 float
+=>
+M(rax int64, xmm0 double) Compound(size: 16)
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_win.expect b/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_win.expect
new file mode 100644
index 0000000..d21ee2b
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct16bytesMixedx10_3/x64_win.expect
@@ -0,0 +1,13 @@
+P(rdx int64) Compound(size: 16)
+P(r8 int64) Compound(size: 16)
+P(r9 int64) Compound(size: 16)
+P(S+0 int64) Compound(size: 16)
+P(S+8 int64) Compound(size: 16)
+P(S+16 int64) Compound(size: 16)
+P(S+24 int64) Compound(size: 16)
+P(S+32 int64) Compound(size: 16)
+P(S+40 int64) Compound(size: 16)
+P(S+48 int64) Compound(size: 16)
+S+56 float
+=>
+P(rcx int64, ret:rax int64) Compound(size: 16)
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_android.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_android.expect
new file mode 100644
index 0000000..025106d
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_android.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 8, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 8, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_ios.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_ios.expect
new file mode 100644
index 0000000..71313bc
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_ios.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 4, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 4, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_linux.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_linux.expect
new file mode 100644
index 0000000..025106d
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_linux.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 8, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 8, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_macos.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_macos.expect
new file mode 100644
index 0000000..025106d
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm64_macos.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 8, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 8, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm_android.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm_android.expect
new file mode 100644
index 0000000..71313bc
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm_android.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 4, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 4, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm_ios.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm_ios.expect
new file mode 100644
index 0000000..71313bc
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm_ios.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 4, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 4, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm_linux.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm_linux.expect
new file mode 100644
index 0000000..71313bc
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/arm_linux.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 4, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 4, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/ia32_android.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/ia32_android.expect
new file mode 100644
index 0000000..71313bc
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/ia32_android.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 4, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 4, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/ia32_linux.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/ia32_linux.expect
new file mode 100644
index 0000000..71313bc
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/ia32_linux.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 4, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 4, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/ia32_win.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/ia32_win.expect
new file mode 100644
index 0000000..71313bc
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/ia32_win.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 4, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 4, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_ios.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_ios.expect
new file mode 100644
index 0000000..025106d
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_ios.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 8, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 8, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_linux.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_linux.expect
new file mode 100644
index 0000000..025106d
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_linux.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 8, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 8, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_macos.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_macos.expect
new file mode 100644
index 0000000..025106d
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_macos.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 8, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 8, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_win.expect b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_win.expect
new file mode 100644
index 0000000..025106d
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_floatarray/x64_win.expect
@@ -0,0 +1,3 @@
+Compound(size: 16, field alignment: 4, stack alignment: 8, members: {
+  0: Array(element type: Compound(size: 8, field alignment: 4, stack alignment: 8, members: {0: Array(element type: float, length: 2)}), length: 2)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_android.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_android.expect
new file mode 100644
index 0000000..a44e66b
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_android.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 8, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_ios.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_ios.expect
new file mode 100644
index 0000000..a44e66b
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_ios.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 8, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_linux.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_linux.expect
new file mode 100644
index 0000000..a44e66b
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_linux.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 8, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_macos.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_macos.expect
new file mode 100644
index 0000000..a44e66b
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm64_macos.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 8, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm_android.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm_android.expect
new file mode 100644
index 0000000..879e00f
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm_android.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 4, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm_ios.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm_ios.expect
new file mode 100644
index 0000000..879e00f
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm_ios.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 4, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm_linux.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm_linux.expect
new file mode 100644
index 0000000..879e00f
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/arm_linux.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 4, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/ia32_android.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/ia32_android.expect
new file mode 100644
index 0000000..879e00f
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/ia32_android.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 4, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/ia32_linux.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/ia32_linux.expect
new file mode 100644
index 0000000..879e00f
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/ia32_linux.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 4, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/ia32_win.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/ia32_win.expect
new file mode 100644
index 0000000..879e00f
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/ia32_win.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 4, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_ios.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_ios.expect
new file mode 100644
index 0000000..a44e66b
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_ios.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 8, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_linux.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_linux.expect
new file mode 100644
index 0000000..a44e66b
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_linux.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 8, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_macos.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_macos.expect
new file mode 100644
index 0000000..a44e66b
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_macos.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 8, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_win.expect b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_win.expect
new file mode 100644
index 0000000..a44e66b
--- /dev/null
+++ b/runtime/vm/compiler/ffi/unit_tests/struct_int8array/x64_win.expect
@@ -0,0 +1,3 @@
+Compound(size: 8, field alignment: 1, stack alignment: 8, members: {
+  0: Array(element type: int8, length: 8)
+})
diff --git a/samples/ffi/calloc.dart b/samples/ffi/calloc.dart
deleted file mode 100644
index e17238a..0000000
--- a/samples/ffi/calloc.dart
+++ /dev/null
@@ -1,109 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int? alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/samples/ffi/resource_management/pool.dart b/samples/ffi/resource_management/pool.dart
index 14e07f4..e37fd22 100644
--- a/samples/ffi/resource_management/pool.dart
+++ b/samples/ffi/resource_management/pool.dart
@@ -9,8 +9,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import '../calloc.dart';
-
 /// An [Allocator] which frees all allocations at the same time.
 ///
 /// The pool allows you to allocate heap memory, but ignores calls to [free].
diff --git a/samples/ffi/resource_management/unmanaged_sample.dart b/samples/ffi/resource_management/unmanaged_sample.dart
index 04c20cb..5ddb6ae 100644
--- a/samples/ffi/resource_management/unmanaged_sample.dart
+++ b/samples/ffi/resource_management/unmanaged_sample.dart
@@ -10,7 +10,6 @@
 import 'package:ffi/ffi.dart';
 
 import 'utf8_helpers.dart';
-import '../calloc.dart';
 import '../dylib_utils.dart';
 
 main() {
diff --git a/samples/ffi/sample_ffi_bitfield.dart b/samples/ffi/sample_ffi_bitfield.dart
index 67ce69e..4508bed 100644
--- a/samples/ffi/sample_ffi_bitfield.dart
+++ b/samples/ffi/sample_ffi_bitfield.dart
@@ -7,8 +7,6 @@
 import 'package:ffi/ffi.dart';
 import 'package:expect/expect.dart';
 
-import 'calloc.dart';
-
 /// typedef struct {
 ///     unsigned int bold      : 1;
 ///     unsigned int underline : 2;
diff --git a/samples/ffi/sample_ffi_data.dart b/samples/ffi/sample_ffi_data.dart
index e5b0497..fd930f1 100644
--- a/samples/ffi/sample_ffi_data.dart
+++ b/samples/ffi/sample_ffi_data.dart
@@ -5,8 +5,6 @@
 import 'dart:ffi';
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
-
 main() {
   print('start main');
 
diff --git a/samples/ffi/sample_ffi_functions.dart b/samples/ffi/sample_ffi_functions.dart
index 4610fa7..4ab9b81 100644
--- a/samples/ffi/sample_ffi_functions.dart
+++ b/samples/ffi/sample_ffi_functions.dart
@@ -6,7 +6,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 typedef NativeUnaryOp = Int32 Function(Int32);
diff --git a/samples/ffi/sample_ffi_functions_callbacks.dart b/samples/ffi/sample_ffi_functions_callbacks.dart
index 19b6212..f571dd1 100644
--- a/samples/ffi/sample_ffi_functions_callbacks.dart
+++ b/samples/ffi/sample_ffi_functions_callbacks.dart
@@ -6,7 +6,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'coordinate.dart';
 import 'dylib_utils.dart';
 
diff --git a/samples/ffi/sample_ffi_functions_structs.dart b/samples/ffi/sample_ffi_functions_structs.dart
index 4bcb9c9..a051fcf 100644
--- a/samples/ffi/sample_ffi_functions_structs.dart
+++ b/samples/ffi/sample_ffi_functions_structs.dart
@@ -6,7 +6,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'coordinate.dart';
 import 'dylib_utils.dart';
 
diff --git a/samples/ffi/sample_ffi_structs.dart b/samples/ffi/sample_ffi_structs.dart
index acad174..ab99ed8 100644
--- a/samples/ffi/sample_ffi_structs.dart
+++ b/samples/ffi/sample_ffi_structs.dart
@@ -6,7 +6,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'coordinate.dart';
 
 main() {
diff --git a/samples/ffi/sqlite/lib/sqlite.dart b/samples/ffi/sqlite/lib/sqlite.dart
index 1e60f9f..d6bac5b 100644
--- a/samples/ffi/sqlite/lib/sqlite.dart
+++ b/samples/ffi/sqlite/lib/sqlite.dart
@@ -8,5 +8,3 @@
 library sqlite;
 
 export "src/database.dart";
-
-export "src/ffi/calloc.dart" show calloc;
diff --git a/samples/ffi/sqlite/lib/src/database.dart b/samples/ffi/sqlite/lib/src/database.dart
index 5031027..b98bf25 100644
--- a/samples/ffi/sqlite/lib/src/database.dart
+++ b/samples/ffi/sqlite/lib/src/database.dart
@@ -15,8 +15,6 @@
 import "bindings/constants.dart";
 import "collections/closable_iterator.dart";
 
-import 'ffi/calloc.dart';
-
 /// [Database] represents an open connection to a SQLite database.
 ///
 /// All functions against a database may throw [SQLiteError].
diff --git a/samples/ffi/sqlite/lib/src/ffi/arena.dart b/samples/ffi/sqlite/lib/src/ffi/arena.dart
index 5369a22..290c2fe 100644
--- a/samples/ffi/sqlite/lib/src/ffi/arena.dart
+++ b/samples/ffi/sqlite/lib/src/ffi/arena.dart
@@ -7,8 +7,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
-
 /// [Arena] manages allocated C memory.
 ///
 /// Arenas are zoned.
diff --git a/samples/ffi/sqlite/lib/src/ffi/calloc.dart b/samples/ffi/sqlite/lib/src/ffi/calloc.dart
deleted file mode 100644
index e17238a..0000000
--- a/samples/ffi/sqlite/lib/src/ffi/calloc.dart
+++ /dev/null
@@ -1,109 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int? alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/samples_2/ffi/calloc.dart b/samples_2/ffi/calloc.dart
deleted file mode 100644
index c6be280..0000000
--- a/samples_2/ffi/calloc.dart
+++ /dev/null
@@ -1,111 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-// @dart=2.9
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/samples_2/ffi/resource_management/pool.dart b/samples_2/ffi/resource_management/pool.dart
index d4610b0..ddb5026 100644
--- a/samples_2/ffi/resource_management/pool.dart
+++ b/samples_2/ffi/resource_management/pool.dart
@@ -11,8 +11,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import '../calloc.dart';
-
 /// An [Allocator] which frees all allocations at the same time.
 ///
 /// The pool allows you to allocate heap memory, but ignores calls to [free].
diff --git a/samples_2/ffi/resource_management/unmanaged_sample.dart b/samples_2/ffi/resource_management/unmanaged_sample.dart
index e73f7cc..fa5a60b 100644
--- a/samples_2/ffi/resource_management/unmanaged_sample.dart
+++ b/samples_2/ffi/resource_management/unmanaged_sample.dart
@@ -12,7 +12,6 @@
 import 'package:ffi/ffi.dart';
 
 import 'utf8_helpers.dart';
-import '../calloc.dart';
 import '../dylib_utils.dart';
 
 main() {
diff --git a/samples_2/ffi/sample_ffi_bitfield.dart b/samples_2/ffi/sample_ffi_bitfield.dart
index 78c41df..43ac425 100644
--- a/samples_2/ffi/sample_ffi_bitfield.dart
+++ b/samples_2/ffi/sample_ffi_bitfield.dart
@@ -9,8 +9,6 @@
 import 'package:ffi/ffi.dart';
 import 'package:expect/expect.dart';
 
-import 'calloc.dart';
-
 /// typedef struct {
 ///     unsigned int bold      : 1;
 ///     unsigned int underline : 2;
diff --git a/samples_2/ffi/sample_ffi_data.dart b/samples_2/ffi/sample_ffi_data.dart
index 2d22011..ba82bec 100644
--- a/samples_2/ffi/sample_ffi_data.dart
+++ b/samples_2/ffi/sample_ffi_data.dart
@@ -7,8 +7,6 @@
 import 'dart:ffi';
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
-
 main() {
   print('start main');
 
diff --git a/samples_2/ffi/sample_ffi_functions.dart b/samples_2/ffi/sample_ffi_functions.dart
index 5142bc4..a0526fa 100644
--- a/samples_2/ffi/sample_ffi_functions.dart
+++ b/samples_2/ffi/sample_ffi_functions.dart
@@ -8,7 +8,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 typedef NativeUnaryOp = Int32 Function(Int32);
diff --git a/samples_2/ffi/sample_ffi_functions_callbacks.dart b/samples_2/ffi/sample_ffi_functions_callbacks.dart
index 35d73c4..4a57f13 100644
--- a/samples_2/ffi/sample_ffi_functions_callbacks.dart
+++ b/samples_2/ffi/sample_ffi_functions_callbacks.dart
@@ -8,7 +8,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'coordinate.dart';
 import 'dylib_utils.dart';
 
diff --git a/samples_2/ffi/sample_ffi_functions_structs.dart b/samples_2/ffi/sample_ffi_functions_structs.dart
index 0d6fa24..7a8370e 100644
--- a/samples_2/ffi/sample_ffi_functions_structs.dart
+++ b/samples_2/ffi/sample_ffi_functions_structs.dart
@@ -8,7 +8,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'coordinate.dart';
 import 'dylib_utils.dart';
 
diff --git a/samples_2/ffi/sample_ffi_structs.dart b/samples_2/ffi/sample_ffi_structs.dart
index 0ce6bca..d384d10 100644
--- a/samples_2/ffi/sample_ffi_structs.dart
+++ b/samples_2/ffi/sample_ffi_structs.dart
@@ -8,7 +8,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'coordinate.dart';
 
 main() {
diff --git a/samples_2/ffi/sqlite/lib/sqlite.dart b/samples_2/ffi/sqlite/lib/sqlite.dart
index 0e0669b..825e434 100644
--- a/samples_2/ffi/sqlite/lib/sqlite.dart
+++ b/samples_2/ffi/sqlite/lib/sqlite.dart
@@ -10,5 +10,3 @@
 library sqlite;
 
 export "src/database.dart";
-
-export "src/ffi/calloc.dart" show calloc;
diff --git a/samples_2/ffi/sqlite/lib/src/database.dart b/samples_2/ffi/sqlite/lib/src/database.dart
index 687fea8..91bcfe6 100644
--- a/samples_2/ffi/sqlite/lib/src/database.dart
+++ b/samples_2/ffi/sqlite/lib/src/database.dart
@@ -17,8 +17,6 @@
 import "bindings/constants.dart";
 import "collections/closable_iterator.dart";
 
-import 'ffi/calloc.dart';
-
 /// [Database] represents an open connection to a SQLite database.
 ///
 /// All functions against a database may throw [SQLiteError].
diff --git a/samples_2/ffi/sqlite/lib/src/ffi/arena.dart b/samples_2/ffi/sqlite/lib/src/ffi/arena.dart
index 39e3035..56b6fea 100644
--- a/samples_2/ffi/sqlite/lib/src/ffi/arena.dart
+++ b/samples_2/ffi/sqlite/lib/src/ffi/arena.dart
@@ -9,8 +9,6 @@
 
 import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
-
 /// [Arena] manages allocated C memory.
 ///
 /// Arenas are zoned.
diff --git a/samples_2/ffi/sqlite/lib/src/ffi/calloc.dart b/samples_2/ffi/sqlite/lib/src/ffi/calloc.dart
deleted file mode 100644
index c6be280..0000000
--- a/samples_2/ffi/sqlite/lib/src/ffi/calloc.dart
+++ /dev/null
@@ -1,111 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-// @dart=2.9
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/tests/ffi/aliasing_test.dart b/tests/ffi/aliasing_test.dart
index 946e1e4..5cace63 100644
--- a/tests/ffi/aliasing_test.dart
+++ b/tests/ffi/aliasing_test.dart
@@ -13,7 +13,6 @@
 import "package:ffi/ffi.dart";
 import "package:expect/expect.dart";
 
-import 'calloc.dart';
 import 'ffi_test_helpers.dart';
 
 void main() {
diff --git a/tests/ffi/calloc.dart b/tests/ffi/calloc.dart
deleted file mode 100644
index e17238a..0000000
--- a/tests/ffi/calloc.dart
+++ /dev/null
@@ -1,109 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int? alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/tests/ffi/calloc_test.dart b/tests/ffi/calloc_test.dart
index b8b9bbf..56f1b97 100644
--- a/tests/ffi/calloc_test.dart
+++ b/tests/ffi/calloc_test.dart
@@ -5,8 +5,8 @@
 import 'dart:ffi';
 
 import 'package:expect/expect.dart';
+import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'coordinate.dart';
 
 void main() {
diff --git a/tests/ffi/data_not_asan_test.dart b/tests/ffi/data_not_asan_test.dart
index 69257d6..b791d71 100644
--- a/tests/ffi/data_not_asan_test.dart
+++ b/tests/ffi/data_not_asan_test.dart
@@ -12,8 +12,6 @@
 import "package:ffi/ffi.dart";
 import "package:expect/expect.dart";
 
-import 'calloc.dart';
-
 void main() {
   testPointerAllocateTooLarge();
   testPointerAllocateNegative();
diff --git a/tests/ffi/data_test.dart b/tests/ffi/data_test.dart
index f2543d1..1a10124 100644
--- a/tests/ffi/data_test.dart
+++ b/tests/ffi/data_test.dart
@@ -11,7 +11,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'ffi_test_helpers.dart';
 
 void main() {
diff --git a/tests/ffi/extension_methods_test.dart b/tests/ffi/extension_methods_test.dart
index 5c688e0e..b8f187e 100644
--- a/tests/ffi/extension_methods_test.dart
+++ b/tests/ffi/extension_methods_test.dart
@@ -7,8 +7,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
-
 main(List<String> arguments) {
   for (int i = 0; i < 100; i++) {
     testStoreLoad();
diff --git a/tests/ffi/external_typed_data_test.dart b/tests/ffi/external_typed_data_test.dart
index 1327dea..17f76eb 100644
--- a/tests/ffi/external_typed_data_test.dart
+++ b/tests/ffi/external_typed_data_test.dart
@@ -9,8 +9,6 @@
 import 'package:expect/expect.dart';
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
-
 main() {
   testInt8Load();
   testInt8Store();
diff --git a/tests/ffi/function_callbacks_structs_by_value_generated_test.dart b/tests/ffi/function_callbacks_structs_by_value_generated_test.dart
index 8fa5b93..b72a008 100644
--- a/tests/ffi/function_callbacks_structs_by_value_generated_test.dart
+++ b/tests/ffi/function_callbacks_structs_by_value_generated_test.dart
@@ -16,7 +16,6 @@
 import "package:ffi/ffi.dart";
 
 import 'callback_tests_utils.dart';
-import 'calloc.dart';
 
 // Reuse the struct classes.
 import 'function_structs_by_value_generated_test.dart';
diff --git a/tests/ffi/function_callbacks_structs_by_value_test.dart b/tests/ffi/function_callbacks_structs_by_value_test.dart
index 2065bc4..d7021b3 100644
--- a/tests/ffi/function_callbacks_structs_by_value_test.dart
+++ b/tests/ffi/function_callbacks_structs_by_value_test.dart
@@ -11,7 +11,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 // Reuse the struct classes.
 import 'function_structs_by_value_generated_test.dart';
 
diff --git a/tests/ffi/function_structs_by_value_generated_test.dart b/tests/ffi/function_structs_by_value_generated_test.dart
index cabe1e6..277e80d 100644
--- a/tests/ffi/function_structs_by_value_generated_test.dart
+++ b/tests/ffi/function_structs_by_value_generated_test.dart
@@ -15,7 +15,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 final ffiTestFunctions = dlopenPlatformSpecific("ffi_test_functions");
diff --git a/tests/ffi/function_structs_test.dart b/tests/ffi/function_structs_test.dart
index 24fc982..d813247 100644
--- a/tests/ffi/function_structs_test.dart
+++ b/tests/ffi/function_structs_test.dart
@@ -12,7 +12,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'coordinate.dart';
 import 'dylib_utils.dart';
 import 'very_large_struct.dart';
diff --git a/tests/ffi/function_test.dart b/tests/ffi/function_test.dart
index 077be64..d5fd3c0 100644
--- a/tests/ffi/function_test.dart
+++ b/tests/ffi/function_test.dart
@@ -18,7 +18,6 @@
 import "package:ffi/ffi.dart";
 import "package:expect/expect.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 void main() {
diff --git a/tests/ffi/generator/structs_by_value_tests_generator.dart b/tests/ffi/generator/structs_by_value_tests_generator.dart
index 3c678d3..f277f68 100644
--- a/tests/ffi/generator/structs_by_value_tests_generator.dart
+++ b/tests/ffi/generator/structs_by_value_tests_generator.dart
@@ -764,7 +764,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 final ffiTestFunctions = dlopenPlatformSpecific("ffi_test_functions");
@@ -817,7 +816,6 @@
 import "package:ffi/ffi.dart";
 
 import 'callback_tests_utils.dart';
-import 'calloc.dart';
 
 // Reuse the struct classes.
 import 'function_structs_by_value_generated_test.dart';
diff --git a/tests/ffi/regress_37254_test.dart b/tests/ffi/regress_37254_test.dart
index 62c71db..0c2829a 100644
--- a/tests/ffi/regress_37254_test.dart
+++ b/tests/ffi/regress_37254_test.dart
@@ -65,8 +65,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
-
 // ===== a.value = b ======
 // The tests follow table cells left to right, top to bottom.
 void store1() {
diff --git a/tests/ffi/regress_39885_test.dart b/tests/ffi/regress_39885_test.dart
index ef73ca7..77de64f 100644
--- a/tests/ffi/regress_39885_test.dart
+++ b/tests/ffi/regress_39885_test.dart
@@ -6,8 +6,6 @@
 
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
-
 main() {
   final data = calloc<Uint8>(3);
   for (int i = 0; i < 3; ++i) {
diff --git a/tests/ffi/regress_43693_test.dart b/tests/ffi/regress_43693_test.dart
index 64b48bf..47e5015 100644
--- a/tests/ffi/regress_43693_test.dart
+++ b/tests/ffi/regress_43693_test.dart
@@ -9,7 +9,6 @@
 import 'package:ffi/ffi.dart';
 import 'package:expect/expect.dart';
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 class Struct43693 extends Struct {
diff --git a/tests/ffi/structs_nested_test.dart b/tests/ffi/structs_nested_test.dart
index c07750e..313b8c4 100644
--- a/tests/ffi/structs_nested_test.dart
+++ b/tests/ffi/structs_nested_test.dart
@@ -11,7 +11,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 final ffiTestFunctions = dlopenPlatformSpecific("ffi_test_functions");
diff --git a/tests/ffi/structs_nnbd_workaround_test.dart b/tests/ffi/structs_nnbd_workaround_test.dart
index 2b361b6..2ed0dca 100644
--- a/tests/ffi/structs_nnbd_workaround_test.dart
+++ b/tests/ffi/structs_nnbd_workaround_test.dart
@@ -11,7 +11,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'coordinate_nnbd_workaround.dart';
 
 void main() {
diff --git a/tests/ffi/structs_test.dart b/tests/ffi/structs_test.dart
index 68ee219..4a5bb8c 100644
--- a/tests/ffi/structs_test.dart
+++ b/tests/ffi/structs_test.dart
@@ -11,7 +11,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'coordinate.dart';
 
 void main() {
diff --git a/tests/ffi/variance_function_test.dart b/tests/ffi/variance_function_test.dart
index 3db0147..04c812c 100644
--- a/tests/ffi/variance_function_test.dart
+++ b/tests/ffi/variance_function_test.dart
@@ -15,7 +15,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 typedef Int64PointerParamOpDart = void Function(Pointer<Int64>);
diff --git a/tests/ffi/vmspecific_enable_ffi_test.dart b/tests/ffi/vmspecific_enable_ffi_test.dart
index ce90607..69ae0aa 100644
--- a/tests/ffi/vmspecific_enable_ffi_test.dart
+++ b/tests/ffi/vmspecific_enable_ffi_test.dart
@@ -10,8 +10,6 @@
 
 import 'package:ffi/ffi.dart'; //# 01: compile-time error
 
-import 'calloc.dart'; //# 01: compile-time error
-
 void main() {
   Pointer<Int8> p = //# 01: compile-time error
       calloc(); //# 01: compile-time error
diff --git a/tests/ffi/vmspecific_static_checks_test.dart b/tests/ffi/vmspecific_static_checks_test.dart
index c2150f8..d0ee2a5 100644
--- a/tests/ffi/vmspecific_static_checks_test.dart
+++ b/tests/ffi/vmspecific_static_checks_test.dart
@@ -10,7 +10,6 @@
 
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 void main() {
diff --git a/tests/ffi_2/aliasing_test.dart b/tests/ffi_2/aliasing_test.dart
index 946e1e4..5cace63 100644
--- a/tests/ffi_2/aliasing_test.dart
+++ b/tests/ffi_2/aliasing_test.dart
@@ -13,7 +13,6 @@
 import "package:ffi/ffi.dart";
 import "package:expect/expect.dart";
 
-import 'calloc.dart';
 import 'ffi_test_helpers.dart';
 
 void main() {
diff --git a/tests/ffi_2/calloc.dart b/tests/ffi_2/calloc.dart
deleted file mode 100644
index a433e39..0000000
--- a/tests/ffi_2/calloc.dart
+++ /dev/null
@@ -1,109 +0,0 @@
-// Copyright (c) 2021, 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.
-
-// TODO(https://dartbug.com/44621): Remove this copy when package:ffi can be
-// rolled. We need to wait until the `Allocator` interface has rolled into
-// Flutter.
-
-import 'dart:ffi';
-import 'dart:io';
-
-final DynamicLibrary stdlib = Platform.isWindows
-    ? DynamicLibrary.open('kernel32.dll')
-    : DynamicLibrary.process();
-
-typedef PosixCallocNative = Pointer Function(IntPtr num, IntPtr size);
-typedef PosixCalloc = Pointer Function(int num, int size);
-final PosixCalloc posixCalloc =
-    stdlib.lookupFunction<PosixCallocNative, PosixCalloc>('calloc');
-
-typedef PosixFreeNative = Void Function(Pointer);
-typedef PosixFree = void Function(Pointer);
-final PosixFree posixFree =
-    stdlib.lookupFunction<PosixFreeNative, PosixFree>('free');
-
-typedef WinGetProcessHeapFn = Pointer Function();
-final WinGetProcessHeapFn winGetProcessHeap = stdlib
-    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>('GetProcessHeap');
-final Pointer processHeap = winGetProcessHeap();
-
-typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
-typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
-final WinHeapAlloc winHeapAlloc =
-    stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>('HeapAlloc');
-
-typedef WinHeapFreeNative = Int32 Function(
-    Pointer heap, Uint32 flags, Pointer memory);
-typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
-final WinHeapFree winHeapFree =
-    stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>('HeapFree');
-
-const int HEAP_ZERO_MEMORY = 8;
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-class _CallocAllocator implements Allocator {
-  const _CallocAllocator();
-
-  /// Allocates [byteCount] bytes of zero-initialized of memory on the native
-  /// heap.
-  ///
-  /// For POSIX-based systems, this uses `calloc`. On Windows, it uses
-  /// `HeapAlloc` against the default public heap.
-  ///
-  /// Throws an [ArgumentError] if the number of bytes or alignment cannot be
-  /// satisfied.
-  // TODO: Stop ignoring alignment if it's large, for example for SSE data.
-  @override
-  Pointer<T> allocate<T extends NativeType>(int byteCount, {int alignment}) {
-    Pointer<T> result;
-    if (Platform.isWindows) {
-      result = winHeapAlloc(processHeap, /*flags=*/ HEAP_ZERO_MEMORY, byteCount)
-          .cast();
-    } else {
-      result = posixCalloc(byteCount, 1).cast();
-    }
-    if (result.address == 0) {
-      throw ArgumentError('Could not allocate $byteCount bytes.');
-    }
-    return result;
-  }
-
-  /// Releases memory allocated on the native heap.
-  ///
-  /// For POSIX-based systems, this uses `free`. On Windows, it uses `HeapFree`
-  /// against the default public heap. It may only be used against pointers
-  /// allocated in a manner equivalent to [allocate].
-  ///
-  /// Throws an [ArgumentError] if the memory pointed to by [pointer] cannot be
-  /// freed.
-  ///
-  // TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
-  // of testing the return integer to be non-zero.
-  @override
-  void free(Pointer pointer) {
-    if (Platform.isWindows) {
-      if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
-        throw ArgumentError('Could not free $pointer.');
-      }
-    } else {
-      posixFree(pointer);
-    }
-  }
-}
-
-/// Manages memory on the native heap.
-///
-/// Initializes newly allocated memory to zero. Use [malloc] for unintialized
-/// memory allocation.
-///
-/// For POSIX-based systems, this uses `calloc` and `free`. On Windows, it uses
-/// `HeapAlloc` with [HEAP_ZERO_MEMORY] and `HeapFree` against the default
-/// public heap.
-const Allocator calloc = _CallocAllocator();
diff --git a/tests/ffi_2/calloc_test.dart b/tests/ffi_2/calloc_test.dart
index b8b9bbf..56f1b97 100644
--- a/tests/ffi_2/calloc_test.dart
+++ b/tests/ffi_2/calloc_test.dart
@@ -5,8 +5,8 @@
 import 'dart:ffi';
 
 import 'package:expect/expect.dart';
+import 'package:ffi/ffi.dart';
 
-import 'calloc.dart';
 import 'coordinate.dart';
 
 void main() {
diff --git a/tests/ffi_2/data_not_asan_test.dart b/tests/ffi_2/data_not_asan_test.dart
index 69257d6..b791d71 100644
--- a/tests/ffi_2/data_not_asan_test.dart
+++ b/tests/ffi_2/data_not_asan_test.dart
@@ -12,8 +12,6 @@
 import "package:ffi/ffi.dart";
 import "package:expect/expect.dart";
 
-import 'calloc.dart';
-
 void main() {
   testPointerAllocateTooLarge();
   testPointerAllocateNegative();
diff --git a/tests/ffi_2/data_test.dart b/tests/ffi_2/data_test.dart
index 59cc7f4..f8ac487e 100644
--- a/tests/ffi_2/data_test.dart
+++ b/tests/ffi_2/data_test.dart
@@ -11,7 +11,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'ffi_test_helpers.dart';
 
 void main() {
diff --git a/tests/ffi_2/extension_methods_test.dart b/tests/ffi_2/extension_methods_test.dart
index 3524a7f..64a6237 100644
--- a/tests/ffi_2/extension_methods_test.dart
+++ b/tests/ffi_2/extension_methods_test.dart
@@ -7,8 +7,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
-
 main(List<String> arguments) {
   for (int i = 0; i < 100; i++) {
     testStoreLoad();
diff --git a/tests/ffi_2/external_typed_data_test.dart b/tests/ffi_2/external_typed_data_test.dart
index 18e8e3c..3c4c71a 100644
--- a/tests/ffi_2/external_typed_data_test.dart
+++ b/tests/ffi_2/external_typed_data_test.dart
@@ -9,8 +9,6 @@
 import 'package:expect/expect.dart';
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
-
 main() {
   testInt8Load();
   testInt8Store();
diff --git a/tests/ffi_2/function_callbacks_structs_by_value_generated_test.dart b/tests/ffi_2/function_callbacks_structs_by_value_generated_test.dart
index 94b19e2..c45e3cb 100644
--- a/tests/ffi_2/function_callbacks_structs_by_value_generated_test.dart
+++ b/tests/ffi_2/function_callbacks_structs_by_value_generated_test.dart
@@ -16,7 +16,6 @@
 import "package:ffi/ffi.dart";
 
 import 'callback_tests_utils.dart';
-import 'calloc.dart';
 
 // Reuse the struct classes.
 import 'function_structs_by_value_generated_test.dart';
diff --git a/tests/ffi_2/function_callbacks_structs_by_value_test.dart b/tests/ffi_2/function_callbacks_structs_by_value_test.dart
index 2065bc4..d7021b3 100644
--- a/tests/ffi_2/function_callbacks_structs_by_value_test.dart
+++ b/tests/ffi_2/function_callbacks_structs_by_value_test.dart
@@ -11,7 +11,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 // Reuse the struct classes.
 import 'function_structs_by_value_generated_test.dart';
 
diff --git a/tests/ffi_2/function_structs_by_value_generated_test.dart b/tests/ffi_2/function_structs_by_value_generated_test.dart
index b44f8e1..ef2996e 100644
--- a/tests/ffi_2/function_structs_by_value_generated_test.dart
+++ b/tests/ffi_2/function_structs_by_value_generated_test.dart
@@ -15,7 +15,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 final ffiTestFunctions = dlopenPlatformSpecific("ffi_test_functions");
diff --git a/tests/ffi_2/function_structs_test.dart b/tests/ffi_2/function_structs_test.dart
index 24fc982..d813247 100644
--- a/tests/ffi_2/function_structs_test.dart
+++ b/tests/ffi_2/function_structs_test.dart
@@ -12,7 +12,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'coordinate.dart';
 import 'dylib_utils.dart';
 import 'very_large_struct.dart';
diff --git a/tests/ffi_2/function_test.dart b/tests/ffi_2/function_test.dart
index b547ffe..d5fd3c0 100644
--- a/tests/ffi_2/function_test.dart
+++ b/tests/ffi_2/function_test.dart
@@ -19,7 +19,6 @@
 import "package:expect/expect.dart";
 
 import 'dylib_utils.dart';
-import 'calloc.dart';
 
 void main() {
   for (int i = 0; i < 100; ++i) {
diff --git a/tests/ffi_2/generator/structs_by_value_tests_generator.dart b/tests/ffi_2/generator/structs_by_value_tests_generator.dart
index 3c678d3..f277f68 100644
--- a/tests/ffi_2/generator/structs_by_value_tests_generator.dart
+++ b/tests/ffi_2/generator/structs_by_value_tests_generator.dart
@@ -764,7 +764,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 final ffiTestFunctions = dlopenPlatformSpecific("ffi_test_functions");
@@ -817,7 +816,6 @@
 import "package:ffi/ffi.dart";
 
 import 'callback_tests_utils.dart';
-import 'calloc.dart';
 
 // Reuse the struct classes.
 import 'function_structs_by_value_generated_test.dart';
diff --git a/tests/ffi_2/null_test.dart b/tests/ffi_2/null_test.dart
index fb51f94..ec7b837 100644
--- a/tests/ffi_2/null_test.dart
+++ b/tests/ffi_2/null_test.dart
@@ -20,7 +20,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 import 'ffi_test_helpers.dart';
 
diff --git a/tests/ffi_2/regress_37254_test.dart b/tests/ffi_2/regress_37254_test.dart
index e73562d..cf2378b 100644
--- a/tests/ffi_2/regress_37254_test.dart
+++ b/tests/ffi_2/regress_37254_test.dart
@@ -65,8 +65,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
-
 // ===== a.value = b ======
 // The tests follow table cells left to right, top to bottom.
 void store1() {
diff --git a/tests/ffi_2/regress_39885_test.dart b/tests/ffi_2/regress_39885_test.dart
index ef73ca7..77de64f 100644
--- a/tests/ffi_2/regress_39885_test.dart
+++ b/tests/ffi_2/regress_39885_test.dart
@@ -6,8 +6,6 @@
 
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
-
 main() {
   final data = calloc<Uint8>(3);
   for (int i = 0; i < 3; ++i) {
diff --git a/tests/ffi_2/regress_43693_test.dart b/tests/ffi_2/regress_43693_test.dart
index b589b0c..01b7cfd 100644
--- a/tests/ffi_2/regress_43693_test.dart
+++ b/tests/ffi_2/regress_43693_test.dart
@@ -9,7 +9,6 @@
 import 'package:ffi/ffi.dart';
 import 'package:expect/expect.dart';
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 class Struct43693 extends Struct {
diff --git a/tests/ffi_2/structs_nested_test.dart b/tests/ffi_2/structs_nested_test.dart
index f48f26c..5bcb1b4 100644
--- a/tests/ffi_2/structs_nested_test.dart
+++ b/tests/ffi_2/structs_nested_test.dart
@@ -11,7 +11,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 final ffiTestFunctions = dlopenPlatformSpecific("ffi_test_functions");
diff --git a/tests/ffi_2/structs_test.dart b/tests/ffi_2/structs_test.dart
index 68ee219..4a5bb8c 100644
--- a/tests/ffi_2/structs_test.dart
+++ b/tests/ffi_2/structs_test.dart
@@ -11,7 +11,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'coordinate.dart';
 
 void main() {
diff --git a/tests/ffi_2/variance_function_test.dart b/tests/ffi_2/variance_function_test.dart
index f53cdfc..210543a 100644
--- a/tests/ffi_2/variance_function_test.dart
+++ b/tests/ffi_2/variance_function_test.dart
@@ -15,7 +15,6 @@
 import "package:expect/expect.dart";
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 typedef Int64PointerParamOpDart = void Function(Pointer<Int64>);
diff --git a/tests/ffi_2/vmspecific_enable_ffi_test.dart b/tests/ffi_2/vmspecific_enable_ffi_test.dart
index ce90607..69ae0aa 100644
--- a/tests/ffi_2/vmspecific_enable_ffi_test.dart
+++ b/tests/ffi_2/vmspecific_enable_ffi_test.dart
@@ -10,8 +10,6 @@
 
 import 'package:ffi/ffi.dart'; //# 01: compile-time error
 
-import 'calloc.dart'; //# 01: compile-time error
-
 void main() {
   Pointer<Int8> p = //# 01: compile-time error
       calloc(); //# 01: compile-time error
diff --git a/tests/ffi_2/vmspecific_static_checks_test.dart b/tests/ffi_2/vmspecific_static_checks_test.dart
index 88e5b2c..ac72dd9 100644
--- a/tests/ffi_2/vmspecific_static_checks_test.dart
+++ b/tests/ffi_2/vmspecific_static_checks_test.dart
@@ -10,7 +10,6 @@
 
 import "package:ffi/ffi.dart";
 
-import 'calloc.dart';
 import 'dylib_utils.dart';
 
 void main() {
diff --git a/tools/VERSION b/tools/VERSION
index f69eca3..3c3c4b9 100644
--- a/tools/VERSION
+++ b/tools/VERSION
@@ -27,5 +27,5 @@
 MAJOR 2
 MINOR 13
 PATCH 0
-PRERELEASE 23
+PRERELEASE 24
 PRERELEASE_PATCH 0
\ No newline at end of file