mapbox / mapbox-gl-native

Interactive, thoroughly customizable maps in native Android, iOS, macOS, Node.js, and Qt applications, powered by vector tiles and OpenGL
https://mapbox.com/mobile
Other
4.34k stars 1.33k forks source link

add/remove annotations and overlays too fast causes deadlock #16623

Open nnhubbard opened 2 years ago

nnhubbard commented 2 years ago

I am having an issue just like #14998 that @bsterry posted, where I am receiving a deadlock when adding or removing annotations or overlays too quickly. Part of the stacktrace:

0   libsystem_kernel.dylib          0x0000000183935130 __psynch_mutexwait + 8
1   libsystem_pthread.dylib         0x0000000183ad8604 _pthread_mutex_lock_wait + 96
2   libsystem_pthread.dylib         0x0000000183ad8550 _pthread_mutex_lock_slow$VARIANT$mp + 260
3   libc++.1.dylib                  0x000000018301ffc4 std::__1::mutex::lock+ 241604 () + 12
4   Mapbox                          0x0000000102e732e8 mbgl::AnnotationManager::addAnnotation+ 357096 (mapbox::util::variant<mbgl::SymbolAnnotation, mbgl::LineAnnotation, mbgl::FillAnnotation> const&) + 56
5   Mapbox                          0x0000000102ecff58 mbgl::Map::addAnnotation+ 737112 (mapbox::util::variant<mbgl::SymbolAnnotation, mbgl::LineAnnotation, mbgl::FillAnnotation> const&) + 44
6   Mapbox                          0x00000001031cd104 -[MGLMapView addAnnotations:] + 3870980 (MGLMapView.mm:0)
7   Mapbox                          0x00000001031cf470 -[MGLMapView addOverlay:] + 3880048 (MGLMapView.mm:4870)

The solution that @julianrex mentioned was to use DispatchQueue.main.async, which I have done this in my subclass.

- (void)addAnnotation:(id<MGLAnnotation>)annotation {

    dispatch_async(dispatch_get_main_queue(), ^{

        [super addAnnotation:annotation];

    });

}

- (void)removeAnnotation:(id<MGLAnnotation>)annotation {

    dispatch_async(dispatch_get_main_queue(), ^{

        [super removeAnnotation:annotation];

    });

}

However, my users testing this still are having crashes with this new code. @julianrex were you suggesting that DispatchQueue.main.async should only be used for removeAnnotations:?

Expected behavior

Annotations and overlays should be added and removed without error.

Actual behavior

Deadlock and crashing if they are added or removed too fast such as when using a clustering framework.

Configuration

Mapbox SDK versions: 5.10 iOS/macOS versions: iOS 13, iOS 14 Device/simulator models: iPhone 11 Pro Max, iPhone 11 Pro, iPhone 6 Xcode version: 12.5

nnhubbard commented 2 years ago

@bsterry Did you ever solve this issue?