Skip to content

zaqwery/objc_ffi_repro

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

1 Commit
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

objc_ffi_repro

Reproduction project for flutter/flutter#187030ArgumentError: Couldn't resolve native function 'OBJC_CLASS_$_NSArray' in 'package:objective_c/objective_c.dylib' escaping objective_c's _getClassOrProto try/catch in a production app.

Important: This project reproduces the throw, not the escape. Here the ArgumentError is caught (the fallback works and the app loads). My production app, with byte-identical config, has the same error escape the catch and crash. This repo exists to show that config, so the difference can be isolated. See "What you'll observe" below.

Environment

Flutter 3.44.0 stable (Dart 3.12.0)
Platform iOS Simulator, Debug (JIT)
iOS toolchain CocoaPods, use_frameworks! + use_modular_headers!
SPM disabled (flutter config enable-swift-package-manager: false)
path_provider_foundation 2.6.0 (forced via dependency_overrides — the FFI/objective_c version)
objective_c 9.4.1 (transitive)

The full dependency set mirrors the production app so the dyld/link graph matches, but lib/main.dart only ever calls path_provider. It also registers both @pragma('vm:entry-point') background isolates (FCM handler + workmanager callback) and performs the first FFI call inside a Riverpod FutureProvider build, matching the production app's call context exactly.

Run

flutter pub get
(cd ios && pod install)
flutter run                       # on an iOS Simulator, Debug

Then enable an "All Exceptions" breakpoint (VS Code: "All Exceptions"; Xcode: Breakpoint Navigator → Exception Breakpoint, all exceptions). A plain "Uncaught Exceptions" breakpoint will not show anything here, because the throw is caught.

What you'll observe

With "All Exceptions" on, execution breaks on the ArgumentError (~3 times, for the absent class symbols), and each time the } on ArgumentError { at objective_c/lib/src/internal.dart:139 catches it, the objc_getClass by-name fallback runs, and the app loads — the UI shows OK docs: ….

The throw and stack are byte-identical to my production app's uncaught crash, through the entire objective_c layer:

ArgumentError: Couldn't resolve native function 'OBJC_CLASS_$_NSArray' …
Native._ffi_resolver_function (dart:ffi-patch/ffi_patch.dart:1943)
_class_NSArray.<anonymous closure>  (objective_c-9.4.1/…/objective_c_bindings_generated.dart:37076)
_getClassOrProto                    (objective_c-9.4.1/…/internal.dart:134)   ← `final p = loader();`, inside the try
getClass                            (objective_c-9.4.1/…/internal.dart:153)
_class_NSArray                      (objective_c-9.4.1/…/objective_c_bindings_generated.dart:37074)
NSArray.fromPointer                 (…:1444)
NSSearchPathForDirectoriesInDomains (path_provider_foundation-2.6.0/lib/src/ffi_bindings.g.dart:29)
getApplicationDocumentsDirectory    (path_provider/lib/path_provider.dart:121)
…  (Riverpod async provider build → ElementWithFuture.handleFuture)

internal.dart:134 is final p = loader();, statically inside the try { (line 133) guarded by } on ArgumentError { (line 139). In this repro that catch fires. In the production app the same ArgumentError, at the same line, escapes the catch and crashes — i.e. the @Native resolver error reaches the program as if the lexical try/catch around loader() were not on the unwind path.

Ruled out as the differentiator

The repro matches the (crashing) production app on all of these and still catches: the objective_c.dylib binary, NativeAssetsManifest.json, the full dependency set, Podfile / use_modular_headers!, the objective_c version (9.4.1), launch method, the Riverpod async-provider call context, both vm:entry-point background isolates, and --dart-define-from-file launch args.

About

Repro for flutter/flutter#187030 — objective_c FFI ArgumentError (OBJC_CLASS_$_NSArray) escaping _getClassOrProto try/catch on Flutter 3.44.0 iOS

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors