Skip to content

Commit cea7f4c

Browse files
rubennortegabrieldonadel
authored andcommitted
Avoid errors when dispatching mount operations within mount hooks (#50091)
Summary: Pull Request resolved: #50091 Changelog: [internal] If a library uses mount hooks to perform mount operations, it's possible to get concurrent modifications of the list of pending surface IDs to report. This fixes that potential error by making a copy of the list before dispatching the mount notifications. Fixes #49783. Reviewed By: javache Differential Revision: D71387739 fbshipit-source-id: 96c723ef2d6bcc659c4452434b7a4d5af26117ef
1 parent 14d0dc5 commit cea7f4c

File tree

1 file changed

+11
-8
lines changed

1 file changed

+11
-8
lines changed

packages/react-native/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java

Lines changed: 11 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -172,7 +172,7 @@ public class FabricUIManager
172172
private final CopyOnWriteArrayList<UIManagerListener> mListeners = new CopyOnWriteArrayList<>();
173173

174174
private boolean mMountNotificationScheduled = false;
175-
private final List<Integer> mMountedSurfaceIds = new ArrayList<>();
175+
private List<Integer> mSurfaceIdsWithPendingMountNotification = new ArrayList<>();
176176

177177
@ThreadConfined(UI)
178178
@NonNull
@@ -1257,12 +1257,13 @@ public void didMountItems(@Nullable List<MountItem> mountItems) {
12571257

12581258
// Collect surface IDs for all the mount items
12591259
for (MountItem mountItem : mountItems) {
1260-
if (mountItem != null && !mMountedSurfaceIds.contains(mountItem.getSurfaceId())) {
1261-
mMountedSurfaceIds.add(mountItem.getSurfaceId());
1260+
if (mountItem != null
1261+
&& !mSurfaceIdsWithPendingMountNotification.contains(mountItem.getSurfaceId())) {
1262+
mSurfaceIdsWithPendingMountNotification.add(mountItem.getSurfaceId());
12621263
}
12631264
}
12641265

1265-
if (!mMountNotificationScheduled && !mMountedSurfaceIds.isEmpty()) {
1266+
if (!mMountNotificationScheduled && !mSurfaceIdsWithPendingMountNotification.isEmpty()) {
12661267
mMountNotificationScheduled = true;
12671268

12681269
// Notify mount when the effects are visible and prevent mount hooks to
@@ -1274,17 +1275,19 @@ public void didMountItems(@Nullable List<MountItem> mountItems) {
12741275
public void run() {
12751276
mMountNotificationScheduled = false;
12761277

1278+
// Create a copy in case mount hooks trigger more mutations
1279+
final List<Integer> surfaceIdsToReportMount =
1280+
mSurfaceIdsWithPendingMountNotification;
1281+
mSurfaceIdsWithPendingMountNotification = new ArrayList<>();
1282+
12771283
final @Nullable Binding binding = mBinding;
12781284
if (binding == null || mDestroyed) {
1279-
mMountedSurfaceIds.clear();
12801285
return;
12811286
}
12821287

1283-
for (int surfaceId : mMountedSurfaceIds) {
1288+
for (int surfaceId : surfaceIdsToReportMount) {
12841289
binding.reportMount(surfaceId);
12851290
}
1286-
1287-
mMountedSurfaceIds.clear();
12881291
}
12891292
});
12901293
}

0 commit comments

Comments
 (0)