Skip to content

MPI Sessions: repeated MPI_Session_init after full finalize deadlocks on macOS (shmem backing-file ENOENT + PMIx fence hang) #14125

Description

@jsquyres

Summary

Repeated MPI Sessions usage — MPI_Session_init after a prior MPI_Session_finalize has dropped the instance refcount to zero — intermittently deadlocks on macOS. The second MPI_Session_init fails to open() the sm/OPAL shmem backing file with ENOENT and then hangs forever in the modex PMIx_Fence_nb wait.

This reproduces on a clean main (no PRs applied), so it is a pre-existing bug, not tied to any in-flight work.

The stock example examples/hello_sessions_c (which does two MPI_Session_init/MPI_Session_finalize cycles) is enough to trigger it; it is what surfaced this, hanging the ompi-pr-builds macOS job.

Environment

  • Open MPI main (6.1.0a1), e.g. f267e427cf; embedded OpenPMIx cb89026, internal PRRTE/hwloc/libevent.
  • GitHub Actions macos-15 runner, arm64, 3 logical CPUs, macOS 15.7.7 (24G720).
  • mpirun --map-by ppr:1:core ./hello_sessions_c → 3 ranks.
  • Built with .opal_ignore removed (all components), but that is not required.

Reproducer

Either the stock example:

/* examples/hello_sessions_c.c: MPI_Session_init/finalize twice */

or, to hit it faster, a loop of full init/finalize cycles:

#include <mpi.h>
#include <stdlib.h>
int main(int argc, char **argv) {
    int iters = (argc > 1) ? atoi(argv[1]) : 100;
    for (int i = 0; i < iters; i++) {
        MPI_Session s;
        MPI_Session_init(MPI_INFO_NULL, MPI_ERRORS_RETURN, &s);
        MPI_Session_finalize(&s);
    }
    return 0;
}

Run repeatedly with multiple local ranks:

mpirun --map-by ppr:1:core ./hello_sessions_c        # loop this; hangs within a handful of runs

A self-contained diagnostic CI workflow that builds Open MPI on macos-15, hammers the example, and on the first hang captures sample/lldb backtraces of every stuck rank + prte and dumps the session directories is here: jsquyres#30 (based on clean main).

Symptom

All ranks print the OPAL shmem/mmap "sys call fail" help on the second MPI_Session_init:

A system call failed during shared memory initialization that should not have.
  System call: open(2)
  Error:       No such file or directory (errno 2)

then the surviving ranks deadlock.

Where it hangs

Both hung ranks are in the second MPI_Session_init (hello_sessions_c.c:17), spinning in the modex fence wait:

main  (hello_sessions_c.c:17)
  MPI_Session_init
    ompi_mpi_instance_init + 3528
      usleep(100)          <-- ~99% of samples

That usleep is OMPI_LAZY_WAIT_FOR_COMPLETION(active) (ompi/runtime/ompi_rte.h:276, while (active) { opal_progress(); usleep(100); }) guarding the modex PMIx_Fence_nb(...) in ompi/instance/instance.c (~line 614). The fence completion callback (fence_release) never fires, so active never clears. prterun itself is healthy/idle (in kevent).

Analysis

The first MPI_Session_finalize takes the instance refcount to zero and tears the entire runtime down — PMIx finalize and removal of the PRRTE/OPAL session directory. The second MPI_Session_init then runs against a torn-down session directory, so:

  1. the sm BTL's OPAL shmem backing-file open() lands in a directory that no longer exists → ENOENT, and
  2. the modex PMIx_Fence_nb never completes → the lazy-wait loop spins forever.

In other words, a full MPI_Session_finalizeMPI_Session_init round-trip does not correctly re-establish the session directory / PMIx fence machinery (at least on macOS). This looks like an OMPI instance ↔ PMIx/PRRTE session-directory lifecycle issue.

Notes

  • Intermittent/probabilistic — it hit iteration 3 of the stock example in the linked run, but the timing window depends on load (a 3-vCPU runner makes it more likely).
  • The sessions_stress loop reproducer makes it far easier to hit.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions