Skip to content

Commit 83aea52

Browse files
committed
Fix lock ordering in dist_monitor() to prevent SMP deadlock
Fix lock ordering in dist_monitor() to prevent SMP deadlock Move synclist_append of remote_monitors after enif_monitor_process() so the monitor is only visible to other threads once fully initialized. This avoids a race where dist_connection_dtor could access a partially initialized monitor entry, and ensures no nested locking occurs between remote_monitors and the locks acquired inside enif_monitor_process.
1 parent c4530b2 commit 83aea52

File tree

1 file changed

+2
-2
lines changed

1 file changed

+2
-2
lines changed

src/libAtomVM/dist_nifs.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -437,12 +437,12 @@ term dist_monitor(struct DistConnection *conn_obj, term from_pid, term target_pr
437437
monitor->ref_len = term_get_external_reference_len(monitor_ref);
438438
memcpy(monitor->ref_words, term_get_external_reference_words(monitor_ref), sizeof(uint32_t) * monitor->ref_len);
439439
if (target_process_id) {
440-
synclist_append(&conn_obj->remote_monitors, &monitor->head);
441440
ErlNifPid target_process_pid = target_process_id;
442441
if (UNLIKELY(enif_monitor_process(erl_nif_env_from_context(ctx), conn_obj, &target_process_pid, &monitor->process_monitor) != 0)) {
443-
synclist_remove(&conn_obj->remote_monitors, &monitor->head);
444442
dist_enqueue_monitor_exit_message(monitor, NOPROC_ATOM, conn_obj, ctx->global);
445443
free(monitor);
444+
} else {
445+
synclist_append(&conn_obj->remote_monitors, &monitor->head);
446446
}
447447
} else {
448448
dist_enqueue_monitor_exit_message(monitor, NOPROC_ATOM, conn_obj, ctx->global);

0 commit comments

Comments
 (0)