@@ -164,6 +164,8 @@ communicate_ghosts_to_owners(MPI_Comm comm, std::span<const int> src,
164
164
// / @param[in] imap An index map.
165
165
// / @param[in] indices List of entity indices (indices local to the
166
166
// / process).
167
+ // / @param[in] order Control the order in which ghost indices appear in
168
+ // / the new map.
167
169
// / @param[in] allow_owner_change Allows indices that are not included
168
170
// / by their owning process but included on sharing processes to be
169
171
// / included in the submap. These indices will be owned by one of the
@@ -176,7 +178,7 @@ std::tuple<std::vector<std::int32_t>, std::vector<std::int32_t>,
176
178
std::vector<int >, std::vector<int >, std::vector<int >>
177
179
compute_submap_indices (const IndexMap& imap,
178
180
std::span<const std::int32_t > indices,
179
- bool allow_owner_change)
181
+ IndexMapOrder order, bool allow_owner_change)
180
182
{
181
183
std::span<const int > src = imap.src ();
182
184
std::span<const int > dest = imap.dest ();
@@ -203,7 +205,7 @@ compute_submap_indices(const IndexMap& imap,
203
205
// `recv_indices` will necessarily be in `indices` on this process, and thus
204
206
// other processes must own them in the submap.
205
207
206
- std::vector<int > recv_owners (send_disp.back ()), submap_dest ;
208
+ std::vector<int > recv_owners (send_disp.back ());
207
209
const int rank = dolfinx::MPI::rank (imap.comm ());
208
210
{
209
211
// Flag to track if the owner of any indices have changed in the submap
@@ -231,11 +233,7 @@ compute_submap_indices(const IndexMap& imap,
231
233
// this process remains its owner in the submap. Otherwise,
232
234
// add the process that sent it to the list of possible owners.
233
235
if (is_in_submap[idx_local])
234
- {
235
236
global_idx_to_possible_owner.push_back ({idx, rank});
236
- // Add the sending process as a destination rank in the submap
237
- submap_dest.push_back (dest[i]);
238
- }
239
237
else
240
238
{
241
239
owners_changed = true ;
@@ -250,10 +248,6 @@ compute_submap_indices(const IndexMap& imap,
250
248
251
249
std::sort (global_idx_to_possible_owner.begin (),
252
250
global_idx_to_possible_owner.end ());
253
- std::sort (submap_dest.begin (), submap_dest.end ());
254
- submap_dest.erase (std::unique (submap_dest.begin (), submap_dest.end ()),
255
- submap_dest.end ());
256
- submap_dest.shrink_to_fit ();
257
251
258
252
// Choose the submap owner for each index in `recv_indices`
259
253
std::vector<int > send_owners;
@@ -350,6 +344,37 @@ compute_submap_indices(const IndexMap& imap,
350
344
submap_src.end ());
351
345
submap_src.shrink_to_fit ();
352
346
347
+ // If required, preserve the order of the ghost indices
348
+ if (order == IndexMapOrder::preserve)
349
+ {
350
+ // Build (old postion, new position) list for ghosts and sort
351
+ std::vector<std::pair<std::int32_t , std::int32_t >> pos;
352
+ pos.reserve (submap_ghost.size ());
353
+ for (std::int32_t idx : submap_ghost)
354
+ pos.emplace_back (idx, pos.size ());
355
+ std::sort (pos.begin (), pos.end ());
356
+
357
+ // Order ghosts in the sub-map by their position in the parent map
358
+ std::vector<int > submap_ghost_owners1;
359
+ submap_ghost_owners1.reserve (submap_ghost_owners.size ());
360
+ std::vector<std::int32_t > submap_ghost1;
361
+ submap_ghost1.reserve (submap_ghost.size ());
362
+ for (auto [_, idx] : pos)
363
+ {
364
+ submap_ghost_owners1.push_back (submap_ghost_owners[idx]);
365
+ submap_ghost1.push_back (submap_ghost[idx]);
366
+ }
367
+
368
+ submap_ghost_owners = std::move (submap_ghost_owners1);
369
+ submap_ghost = std::move (submap_ghost1);
370
+ }
371
+
372
+ // Compute submap destination ranks
373
+ // FIXME Remove call to NBX
374
+ std::vector<int > submap_dest
375
+ = dolfinx::MPI::compute_graph_edges_nbx (imap.comm (), submap_src);
376
+ std::sort (submap_dest.begin (), submap_dest.end ());
377
+
353
378
return {std::move (submap_owned), std::move (submap_ghost),
354
379
std::move (submap_ghost_owners), std::move (submap_src),
355
380
std::move (submap_dest)};
@@ -725,14 +750,14 @@ common::stack_index_maps(
725
750
std::pair<IndexMap, std::vector<std::int32_t >>
726
751
common::create_sub_index_map (const IndexMap& imap,
727
752
std::span<const std::int32_t > indices,
728
- bool allow_owner_change)
753
+ IndexMapOrder order, bool allow_owner_change)
729
754
{
730
755
// Compute the owned, ghost, and ghost owners of submap indices.
731
756
// NOTE: All indices are local and numbered w.r.t. the original (imap)
732
757
// index map
733
- const auto [submap_owned, submap_ghost, submap_ghost_owners, submap_src,
734
- submap_dest]
735
- = compute_submap_indices (imap, indices, allow_owner_change);
758
+ auto [submap_owned, submap_ghost, submap_ghost_owners, submap_src,
759
+ submap_dest]
760
+ = compute_submap_indices (imap, indices, order, allow_owner_change);
736
761
737
762
// Compute submap offset for this rank
738
763
std::int64_t submap_local_size = submap_owned.size ();
0 commit comments