Skip to content

Split comm method#89

Draft
TomMelt wants to merge 9 commits into
mainfrom
split-comm-method
Draft

Split comm method#89
TomMelt wants to merge 9 commits into
mainfrom
split-comm-method

Conversation

@TomMelt

@TomMelt TomMelt commented Jun 25, 2026

Copy link
Copy Markdown
Contributor

WIP Do Not Merge

Two-stage tripolar domain decomposition using split MPI communicators

fixes #85

Summary

Implement two-stage tripolar domain decomposition: when the --tripolar flag is passed, the domain is split East/West by coordinate via MPI_Comm_split, each half is partitioned independently with Zoltan, and results are merged back into a single global partitioning. The base partition() flow is preserved for non-tripolar runs.

Changes

main.cpp

  • Add --tripolar (-t) CLI flag to enable split-communicator mode
  • Split MPI_COMM_WORLD into East/West sub-communicators using MPI_Comm_split (color = 0 West, 1 East, midpoint = globalExt[0] / 2)
  • Create a copy of the grid (subgrid) for sub-communicator work
  • Run partitioning on subgrid + subpartitioner within each sub-communicator, or fall through to standard single-communicator path
  • Merge sub-partitioner results back into the original partitioner: copy GlobalNew, LocalExtNew, and adjust ProcId offsets for the East half
  • Call discover_neighbours() after merge to rebuild neighbour info on the unified communicator
  • Clean up sub-communicator and subgrid resources

Grid.cpp / Grid.hpp

  • Replace deleted copy constructor with an explicit Grid(const Grid& other) copy ctor (needed for subgrid creation)
  • Add set_comm(), set_global(), set_globalExt() setters to allow reconfiguring a grid copy for sub-communicator use
  • Add recompute_ids() to regenerate _global_id / _local_id after the grid's bounding box changes (East/West halves get different global positions)
  • Add _ignore_mask member (defaults false) to control whether the land mask is applied during id recomputation

Partitioner.cpp / Partitioner.hpp

  • Move discover_neighbours() from protected to public
  • Add initialize(Grid&) virtual method to base Partitioner — extracts grid extents/bounding-box/periodicity into partitioner member variables, separating setup from partitioning
  • Add a large set of getter/setter accessors: setTotalNumProcs, setComm, get/setLocalExtNew, get/setGlobalNew, get/setGlobal, get/setGlobalExt, get/setProcId

ZoltanPartitioner.cpp / ZoltanPartitioner.hpp

  • Implement initialize(Grid&) by copying the grid setup logic previously inside partition()
  • Have partition(Grid&) call initialize(grid) first, preserving all original partitioning logic
  • Remove duplicate discover_neighbours() call from inside partition() (now called once after merge in main)

TomMelt and others added 8 commits June 16, 2026 17:05
- Implement Grid copy constructor (previously deleted)
- Add set_global(), set_globalExt(), and recompute_ids() to allow
modification of grid geometry after construction
- In tripolar mode, partition a subgrid copy with adjusted extents
instead of the original grid
Add setter/getter accessors for internal partitioning state (total
number of procs, communicator, global coordinates, local extents) on
both Partitioner and Grid classes.

Moves discover_neighbours() from private to public so it can be called
after partition results are populated.
For tripolar mode, create a separate subpartitioner for each sub-grid,
then merge the results into the main partitioner before calling
discover_neighbours().

This also enables metadata saving in tripolar mode by removing the
previous known limitation.
Move the 6 grid-loading statements from ZoltanPartitioner::partition()
into a new ZoltanPartitioner::initialize(Grid&) method. Add the
corresponding initialize() method to the Partitioner base class as a
pure virtual function so all future partitioners must implement it.

This improves separation of concerns: initialize() handles setting
method variables (_numProcs, _globalExt, _global, _localExt, _px, _py)
from the grid, while partition() focuses on the partitioning logic
itself.
Expose the process ID vector of the latest 2D domain decomposition
via getter and setter methods.
…ar mode

- Move the MPI color variable outside the tripolar conditional so it's
  available for downstream use.
- Add partitioner initialization for the tripolar case.
- Remove redundant setTotalNumProcs/setGlobalExt calls.
- Offset process IDs of the East half (color==1) by numProcs/2 to avoid
  duplicates when merging results from both sub-communicators.
- Restore mask and metadata saving for both tripolar and non-tripolar
  modes.
@TomMelt TomMelt added the ICCS label Jun 25, 2026
@TomMelt TomMelt moved this to Review required in neXtSIM_DG overview Jun 25, 2026
@TomMelt TomMelt self-assigned this Jul 6, 2026
@TomMelt TomMelt marked this pull request as draft July 6, 2026 13:11
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

Status: Review required

Development

Successfully merging this pull request may close these issues.

Manually split domain

1 participant