7#ifndef HEFFTE_GEOMETRY_H
8#define HEFFTE_GEOMETRY_H
12#include "heffte_utils.h"
66template<
typename index =
int>
82 std::array<index, 3>{corder[0], corder[1], 2}){}
87 (
static_cast<long long>(
size[0]) *
static_cast<long long>(
size[1]) *
static_cast<long long>(
size[2])); }
96 if (
empty())
return box3d({0, 0, 0}, {-1, -1, -1});
108 return not (*
this != other);
112 for(
int i=0;
i<3;
i++)
125 std::array<index, 3>
const low;
127 std::array<index, 3>
const high;
129 std::array<index, 3>
const size;
138template<
typename index =
int>
145template<
typename index>
147 for(
int i=0;
i<3;
i++)
148 os <<
box.low[
i] <<
" " <<
box.high[
i] <<
" (" <<
box.size[
i] <<
")\n";
149 os <<
"(" <<
box.order[0] <<
"," <<
box.order[1] <<
"," <<
box.order[2] <<
")\n";
158template<
typename index>
162 return box.osize(0) *
box.osize(1);
168template<
typename index>
172 return box.osize(0) *
box.osize(1);
212template<
typename index =
int>
215 std::vector<box3d<index>>
in;
217 std::vector<box3d<index>>
out;
228template<
typename index>
230 std::array<index, 3> low =
boxes[0].low;
231 std::array<index, 3> high =
boxes[0].high;
233 for(index
i=0;
i<3;
i++)
234 low[
i] = std::min(low[
i],
b.low[
i]);
235 for(index
i=0;
i<3;
i++)
236 high[
i] = std::max(high[
i],
b.high[
i]);
245template<
typename index>
265template<
typename index>
270 throw std::invalid_argument(
"The provided input boxes do not fill the world box!");
272 for(
size_t i=0;
i<3;
i++)
274 throw std::invalid_argument(
"Global box indexing must start from 0!");
276 for(
size_t i=0;
i<
boxes.size();
i++)
277 for(
size_t j=0;
j<
boxes.size();
j++)
279 throw std::invalid_argument(
"Input boxes cannot overlap!");
302 std::vector<std::array<int, 2>>
result;
303 for(
int i=1;
i<=
n;
i++){
338 std::array<int, 2>
min_array = factors.front();
340 for(
auto f : factors){
361template<
typename index>
364 ->std::array<int, 3>{
367 std::array<int, 3>{
grid[0],
grid[1], 1});
371 auto valid = [&](std::array<int, 3>
const &
grid)
385 for(
auto const &
g : factors){
392 if (
not valid(
result))
throw std::runtime_error(
"Cannot split the given number of indexes into the given set of mpi-ranks. Most liklely, the number of indexes is too small compared to the number of mpi-ranks.");
408template<
typename index>
415 std::vector<box3d<index>>
result;
428 for(
size_t i=0;
i<
remap.map.size();
i++)
430 box3d<index>(std::array<index, 3>{0, 0, 0}, std::array<index, 3>{-1, -1, -1},
world.order) :
441template<
typename index>
453template<
typename index>
465template<
typename index>
467 std::vector<box3d<index>>
result;
469 for(
auto const &
b :
shape)
488template<
typename index>
491 std::array<int, 3>
const order,
493 std::vector<box3d<index>>
result;
497 for(
size_t i=0;
i<
remap.map.size();
i++)
534template<
typename index>
567template<
typename index>
572 std::array<int, 3>
const order,
581 std::vector<box3d<index>>
pencilsA =
585 std::vector<box3d<index>>
pencilsB =
598template<
typename index>
602 std::array<int, 3>
const order,
606 std::vector<box3d<index>>
slabs;
642template<
typename index>
654 std::valarray<index>
best_grid = {1, 1, 1};
660 return ( box_size * box_size.cshift(1) ).
sum();
706template<
typename index>
int fft1d_get_howmany(box3d< index > const box, int const dimension)
Return the number of 1-D ffts contained in the box in the given dimension.
Definition heffte_geometry.h:159
int fft1d_get_stride(box3d< index > const box, int const dimension)
Return the stride of the 1-D ffts contained in the box in the given dimension.
Definition heffte_geometry.h:169
bool match(std::vector< box3d< index > > const &shape0, std::vector< box3d< index > > const &shape1)
Compares two vectors of boxes, returns true if all boxes match.
Definition heffte_geometry.h:246
bool is_slab(box3d< index > const world, std::vector< box3d< index > > const &shape, int direction1, int direction2)
Returns true if the shape forms slabs in the given directions.
Definition heffte_geometry.h:454
long long count_connections(std::vector< box3d< index > > const &new_boxes, std::vector< box3d< index > > const &old_boxes)
Counts the number of point-to-point connections between the old and new box geometries.
Definition heffte_geometry.h:535
std::vector< box3d< index > > make_pencils(box3d< index > const world, std::array< int, 2 > const proc_grid, int const dimension, std::vector< box3d< index > > const &source, std::array< int, 3 > const order, rank_remap const &remap=rank_remap())
Breaks the world into a grid of pencils and orders the pencils to the ranks that will minimize commun...
Definition heffte_geometry.h:568
box3d< index > find_world(std::vector< box3d< index > > const &boxes)
Returns the box that encapsulates all other boxes.
Definition heffte_geometry.h:229
std::vector< box3d< index > > reorder(std::vector< box3d< index > > const &shape, std::array< int, 3 > order)
Returns the same shape, but sets a different order for each box.
Definition heffte_geometry.h:466
bool world_complete(std::vector< box3d< index > > const &boxes, box3d< index > const world)
Returns true if the geometry of the world is as expected.
Definition heffte_geometry.h:266
bool is_pencils(box3d< index > const world, std::vector< box3d< index > > const &shape, int direction)
Returns true if the shape forms pencils in the given direction.
Definition heffte_geometry.h:442
std::vector< box3d< index > > split_world(box3d< index > const world, std::array< int, 3 > const proc_grid, rank_remap const &remap=rank_remap())
Splits the world box into a set of boxes that will be assigned to a process in the process grid.
Definition heffte_geometry.h:409
std::vector< box3d< index > > make_slabs(box3d< index > const world, int num_slabs, int const dimension1, int const dimension2, std::vector< box3d< index > > const &source, std::array< int, 3 > const order, rank_remap const &remap)
Breaks the world into a set of slabs that span the given dimensions.
Definition heffte_geometry.h:599
std::array< int, 3 > proc_setup_min_surface(box3d< index > const world, int num_procs)
Creates a grid of mpi-ranks that will minimize the area of each of the boxes.
Definition heffte_geometry.h:643
std::vector< box3d< index > > maximize_overlap(std::vector< box3d< index > > const &new_boxes, std::vector< box3d< index > > const &old_boxes, std::array< int, 3 > const order, rank_remap const &remap)
Shuffle the new boxes to maximize the overlap with the old boxes.
Definition heffte_geometry.h:489
std::ostream & operator<<(std::ostream &os, box3d< index > const box)
Debugging info, writes out the box to a stream.
Definition heffte_geometry.h:146
direction
Indicates the direction of the FFT (internal use only).
Definition heffte_common.h:652
int get_area(std::array< int, 2 > const &dims)
Get the surface area of a processor grid.
Definition heffte_geometry.h:321
std::array< int, 3 > make_procgrid2d(box3d< index > const world, int direction_1d, std::array< int, 2 > const candidate_grid)
Factorize the MPI ranks into a 2D grid with specific constraints.
Definition heffte_geometry.h:362
std::array< int, 2 > make_procgrid(int const num_procs)
Factorize the MPI ranks into a 2D grid.
Definition heffte_geometry.h:336
int comm_rank(MPI_Comm const comm)
Returns the rank of this process within the specified comm.
Definition heffte_utils.h:79
int comm_size(MPI_Comm const comm)
Returns the size of the specified communicator.
Definition heffte_utils.h:136
ioboxes< index > gather_boxes(box3d< index > const my_inbox, box3d< index > const my_outbox, MPI_Comm const comm)
Gather all boxes across all ranks in the comm.
Definition heffte_geometry.h:707
Namespace containing all HeFFTe methods and classes.
Definition heffte_backend_cuda.h:38
std::vector< std::array< int, 2 > > get_factors(int const n)
fft3dmisc
Definition heffte_geometry.h:301
A generic container that describes a 3d box of indexes.
Definition heffte_geometry.h:67
box3d(std::array< index, 3 > clow, std::array< index, 3 > chigh)
Constructs a box from the low and high indexes, the span in each direction includes the low and high ...
Definition heffte_geometry.h:69
box3d collide(box3d const other) const
Creates a box that holds the intersection of this box and the other.
Definition heffte_geometry.h:89
bool operator!=(box3d const &other) const
Compares two boxes, ignoring the order, returns true if either of the box boundaries do not match.
Definition heffte_geometry.h:111
bool operator==(box3d const &other) const
Compares two boxes, ignoring the order, returns true if all sizes and boundaries match.
Definition heffte_geometry.h:107
bool empty() const
Returns true if the box contains no indexes.
Definition heffte_geometry.h:84
bool is2d() const
Returns true if either dimension contains only a single index.
Definition heffte_geometry.h:105
box3d(std::array< index, 3 > clow, std::array< index, 3 > chigh, std::array< int, 3 > corder)
Constructs a box from the low and high indexes, also sets an order.
Definition heffte_geometry.h:73
std::array< index, 3 > const size
The number of indexes in each direction.
Definition heffte_geometry.h:129
box3d r2c(int dimension) const
Returns the box that is reduced in the given dimension according to the real-to-complex symmetry.
Definition heffte_geometry.h:95
long long count() const
Counts all indexes in the box, i.e., the volume.
Definition heffte_geometry.h:86
bool ordered_same_as(box3d const &other) const
Compares the order of two boxes, ignores the dimensions, returns true if the order is the same.
Definition heffte_geometry.h:117
std::array< index, 3 > const low
The three lowest indexes.
Definition heffte_geometry.h:125
box3d(std::array< index, 2 > clow, std::array< index, 2 > chigh)
Constructor for the two dimensional case.
Definition heffte_geometry.h:77
int find_order(int dir) const
Returns the effective order of the direction (dir), 0 -> fast, 1 -> mid, 2 -> slow.
Definition heffte_geometry.h:121
std::array< index, 3 > const high
The three highest indexes.
Definition heffte_geometry.h:127
box3d(std::array< index, 2 > clow, std::array< index, 2 > chigh, std::array< int, 2 > corder)
Constructor for the two dimensional case, order is either (0, 1) or (1, 0).
Definition heffte_geometry.h:80
std::array< int, 3 > const order
The order of the dimensions in the k * plane_stride + j * line_stride + i indexing.
Definition heffte_geometry.h:131
index osize(int dimension) const
Get the ordered size of the dimension, i.e., size[order[dimension]].
Definition heffte_geometry.h:123
Pair of lists of input-output boxes as used by the heffte::fft3d.
Definition heffte_geometry.h:213
std::vector< box3d< index > > in
Inboxes for all ranks across the comm.
Definition heffte_geometry.h:215
std::vector< box3d< index > > out
Outboxes for all ranks across the comm.
Definition heffte_geometry.h:217
Wrapper around cufftHandle plans, set for float or double complex.
Definition heffte_backend_cuda.h:346
Keeps the local rank and the map from the global rank to the sub-ranks used in the work.
Definition heffte_geometry.h:179
int const mpi_rank
The local rank.
Definition heffte_geometry.h:185
void set_subranks(size_t all_ranks, int sub_ranks)
Build the map when using fixed number of sub-ranks.
Definition heffte_geometry.h:189
void set_subranks(MPI_Comm global, MPI_Comm subcomm)
Build the map when using user provided sub-communicator.
Definition heffte_geometry.h:195
bool empty() const
Indicates whether the remap is empty.
Definition heffte_geometry.h:203
int size_subcomm
The number of ranks in the sub-comm.
Definition heffte_geometry.h:201
rank_remap(int rank)
Creates a new remap and initializes only the mpi_rank.
Definition heffte_geometry.h:183
std::vector< int > map
Global to local map.
Definition heffte_geometry.h:187
rank_remap()
Default constructor.
Definition heffte_geometry.h:181