Block-Structured AMR Software Framework
Distribution.H
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2017, UChicago Argonne, LLC
3  * All Rights Reserved
4  *
5  * Hardware/Hybrid Cosmology Code (HACC), Version 1.0
6  *
7  * Salman Habib, Adrian Pope, Hal Finkel, Nicholas Frontiere, Katrin Heitmann,
8  * Vitali Morozov, Jeffrey Emberson, Thomas Uram, Esteban Rangel
9  * (Argonne National Laboratory)
10  *
11  * David Daniel, Patricia Fasel, Chung-Hsing Hsu, Zarija Lukic, James Ahrens
12  * (Los Alamos National Laboratory)
13  *
14  * George Zagaris
15  * (Kitware)
16  *
17  * OPEN SOURCE LICENSE
18  *
19  * Redistribution and use in source and binary forms, with or without
20  * modification, are permitted provided that the following conditions are met:
21  *
22  * 1. Redistributions of source code must retain the above copyright notice,
23  * this list of conditions and the following disclaimer. Software changes,
24  * modifications, or derivative works, should be noted with comments and
25  * the author and organization's name.
26  *
27  * 2. Redistributions in binary form must reproduce the above copyright
28  * notice, this list of conditions and the following disclaimer in the
29  * documentation and/or other materials provided with the distribution.
30  *
31  * 3. Neither the names of UChicago Argonne, LLC or the Department of Energy
32  * nor the names of its contributors may be used to endorse or promote
33  * products derived from this software without specific prior written
34  * permission.
35  *
36  * 4. The software and the end-user documentation included with the
37  * redistribution, if any, must include the following acknowledgment:
38  *
39  * "This product includes software produced by UChicago Argonne, LLC under
40  * Contract No. DE-AC02-06CH11357 with the Department of Energy."
41  *
42  * *****************************************************************************
43  * DISCLAIMER
44  * THE SOFTWARE IS SUPPLIED "AS IS" WITHOUT WARRANTY OF ANY KIND. NEITHER THE
45  * UNITED STATES GOVERNMENT, NOR THE UNITED STATES DEPARTMENT OF ENERGY, NOR
46  * UCHICAGO ARGONNE, LLC, NOR ANY OF THEIR EMPLOYEES, MAKES ANY WARRANTY,
47  * EXPRESS OR IMPLIED, OR ASSUMES ANY LEGAL LIABILITY OR RESPONSIBILITY FOR THE
48  * ACCURARY, COMPLETENESS, OR USEFULNESS OF ANY INFORMATION, DATA, APPARATUS,
49  * PRODUCT, OR PROCESS DISCLOSED, OR REPRESENTS THAT ITS USE WOULD NOT INFRINGE
50  * PRIVATELY OWNED RIGHTS.
51  *
52  * *****************************************************************************
53  */
54 
55 // I think this should work for global {ngx, ngy, ngz}
56 
57 #ifndef HACC_DISTRIBUTION_HPP
58 #define HACC_DISTRIBUTION_HPP
59 
60 #include <vector>
61 
63 // Distribution / partition / decomposition of data
64 //
65 // A C++ wrapper around distribution.h
67 
68 #include "complex-type.h"
69 #include "distribution_c.h"
70 
71 namespace hacc {
72 
73 class Distribution {
74 
75 public:
76 
77 
78  //
79  // constructors
80  //
81 
82  // standard setup
83 
85  int const n[],
86  bool debug = false)
87  : m_comm(comm), m_rmap(NULL), m_debug(debug)
88  {
89  int Ndims[3] = { 0, 0, 0 };
90  initialize(comm, n, Ndims);
91  }
92 
94  int ng,
95  bool debug = false)
96  : m_comm(comm), m_rmap(NULL), m_debug(debug)
97  {
98  int n[3] = { ng, ng, ng };
99  int Ndims[3] = { 0, 0, 0 };
100  initialize(comm, n, Ndims);
101  }
102 
103  // custom setup with 3d decomposition and grid to rank map
104 
106  int const n[],
107  int const Ndims[],
108  int *rmap,
109  bool debug = false)
110  : m_comm(comm), m_rmap(rmap), m_debug(debug)
111  {
112  initialize(comm, n, Ndims);
113  }
114 
116  int ng,
117  int const Ndims[],
118  int *rmap,
119  bool debug = false)
120  : m_comm(comm), m_rmap(rmap), m_debug(debug)
121  {
122  int n[3] = { ng, ng, ng };
123  initialize(comm, n, Ndims);
124  }
125 
126  //
127  // destructor
128  //
129 
130  virtual ~Distribution()
131  {
133  }
134 
135 
136  // initialization
137 
138  void initialize(MPI_Comm comm, int const n[], int const Ndims[]) {
139  int flag;
140  MPI_Initialized(&flag);
141  if (flag == 0) {
142  MPI_Init(0, 0);
143  }
144 
145  distribution_init(comm, n, Ndims, &m_d, m_rmap, m_debug);
146  }
147 
148 
149  // redistribution
150 
152  distribution_1_to_3(a, b, &m_d);
153  }
154 
156  distribution_3_to_1(a, b, &m_d);
157  }
158 
159  void redistribute_2_to_3(const complex_t *a, complex_t *b, int axis) {
160  distribution_2_to_3(a, b, &m_d, axis);
161  }
162 
163  void redistribute_3_to_2(const complex_t *a, complex_t *b, int axis) {
164  distribution_3_to_2(a, b, &m_d, axis);
165  }
166 
167 
168  // grid sizes
169 
170  size_t local_size() const {
171  size_t size = 1;
172  for (int i = 0; i < 3; ++i) {
173  size *= (m_d.n[i] / m_d.process_topology_3.nproc[i]);
174  }
175  return size;
176  }
177 
178  size_t global_size() const {
179  size_t size = 1;
180  for (int i = 0; i < 3; ++i) {
181  size *= m_d.n[i];
182  }
183  return size;
184  }
185 
186  int global_ng(int i) const { return m_d.n[i];}
187  int local_ng_1d(int i) const { return m_d.process_topology_1.n[i];}
188  int local_ng_2d_x(int i) const { return m_d.process_topology_2_x.n[i];}
189  int local_ng_2d_y(int i) const { return m_d.process_topology_2_y.n[i];}
190  int local_ng_2d_z(int i) const { return m_d.process_topology_2_z.n[i];}
191  int local_ng_3d(int i) const { return m_d.process_topology_3.n[i];}
192 
193  int const (& global_ng() const)[3] { return m_d.n;}
194  int const (& local_ng_1d() const)[3] { return m_d.process_topology_1.n;}
195  int const (& local_ng_2d_x() const)[3] { return m_d.process_topology_2_x.n;}
196  int const (& local_ng_2d_y() const)[3] { return m_d.process_topology_2_y.n;}
197  int const (& local_ng_2d_z() const)[3] { return m_d.process_topology_2_z.n;}
198  int const (& local_ng_3d() const)[3] { return m_d.process_topology_3.n;}
199 
200 
201  // numbers of ranks
202 
203  int nproc() const { return m_d.process_topology_1.nproc[0];}
204 
205  int nproc_1d(int i) const { return m_d.process_topology_1.nproc[i];}
206  int nproc_2d_x(int i) const { return m_d.process_topology_2_x.nproc[i];}
207  int nproc_2d_y(int i) const { return m_d.process_topology_2_y.nproc[i];}
208  int nproc_2d_z(int i) const { return m_d.process_topology_2_z.nproc[i];}
209  int nproc_3d(int i) const { return m_d.process_topology_3.nproc[i];}
210 
211  int const (& nproc_1d() const)[3] { return m_d.process_topology_1.nproc;}
212  int const (& nproc_2d_x() const)[3] { return m_d.process_topology_2_x.nproc;}
213  int const (& nproc_2d_y() const)[3] { return m_d.process_topology_2_y.nproc;}
214  int const (& nproc_2d_z() const)[3] { return m_d.process_topology_2_z.nproc;}
215  int const (& nproc_3d() const)[3] { return m_d.process_topology_3.nproc;}
216 
217 
218  // rank location
219 
220  int self() const { return m_d.process_topology_1.self[0];}
221 
222  int self_1d(int i) const { return m_d.process_topology_1.self[i];}
223  int self_2d_x(int i) const { return m_d.process_topology_2_x.self[i];}
224  int self_2d_y(int i) const { return m_d.process_topology_2_y.self[i];}
225  int self_2d_z(int i) const { return m_d.process_topology_2_z.self[i];}
226  int self_3d(int i) const { return m_d.process_topology_3.self[i];}
227 
228  int const (& self_1d() const)[3] { return m_d.process_topology_1.self;}
229  int const (& self_2d_x() const)[3] { return m_d.process_topology_2_x.self;}
230  int const (& self_2d_y() const)[3] { return m_d.process_topology_2_y.self;}
231  int const (& self_2d_z() const)[3] { return m_d.process_topology_2_z.self;}
232  int const (& self_3d() const)[3] { return m_d.process_topology_3.self;}
233 
234 
235  // communicators
236 
242 
243  MPI_Comm parent_comm() const { return m_comm;}
244 
245 
246  //
247 
248  int rank_2d_x(int c[]) {
249  int r;
250  Rank_x_pencils(&r, c, &m_d);
251  return r;
252  }
253 
254  int rank_2d_y(int c[]) {
255  int r;
256  Rank_y_pencils(&r, c, &m_d);
257  return r;
258  }
259 
260  int rank_2d_z(int c[]) {
261  int r;
262  Rank_z_pencils(&r, c, &m_d);
263  return r;
264  }
265 
266 
267  //
268 
269  void coords_2d_x(int r, int c[]) { Coord_x_pencils(r, c, &m_d);}
270  void coords_2d_y(int r, int c[]) { Coord_y_pencils(r, c, &m_d);}
271  void coords_2d_z(int r, int c[]) { Coord_z_pencils(r, c, &m_d);}
272 
273 
274 public:
275  // This is public for now until we refactor the Solver* classes
276  // to use the C++ interface.
278 
279 protected:
281  int* m_rmap;
282  bool m_debug;
283 };
284 
285 } // namespace hacc
286 #endif // HACC_DISTRIBUTION_HPP
int MPI_Comm
Definition: AMReX_ccse-mpi.H:47
Definition: Distribution.H:73
void coords_2d_x(int r, int c[])
Definition: Distribution.H:269
int * m_rmap
Definition: Distribution.H:281
int const (& self_2d_z() const)[3]
Definition: Distribution.H:231
int local_ng_1d(int i) const
Definition: Distribution.H:187
int nproc_1d(int i) const
Definition: Distribution.H:205
MPI_Comm cart_1d() const
Definition: Distribution.H:237
void redistribute_1_to_3(const complex_t *a, complex_t *b)
Definition: Distribution.H:151
int const (& local_ng_1d() const)[3]
Definition: Distribution.H:194
size_t global_size() const
Definition: Distribution.H:178
int local_ng_2d_y(int i) const
Definition: Distribution.H:189
MPI_Comm parent_comm() const
Definition: Distribution.H:243
int const (& local_ng_2d_x() const)[3]
Definition: Distribution.H:195
int nproc() const
Definition: Distribution.H:203
Distribution(MPI_Comm comm, int const n[], bool debug=false)
Definition: Distribution.H:84
int const (& nproc_1d() const)[3]
Definition: Distribution.H:211
int const (& self_3d() const)[3]
Definition: Distribution.H:232
int const (& local_ng_3d() const)[3]
Definition: Distribution.H:198
MPI_Comm cart_3d() const
Definition: Distribution.H:241
void coords_2d_z(int r, int c[])
Definition: Distribution.H:271
MPI_Comm cart_2d_y() const
Definition: Distribution.H:239
MPI_Comm m_comm
Definition: Distribution.H:280
MPI_Comm cart_2d_x() const
Definition: Distribution.H:238
int local_ng_3d(int i) const
Definition: Distribution.H:191
void coords_2d_y(int r, int c[])
Definition: Distribution.H:270
int global_ng(int i) const
Definition: Distribution.H:186
void initialize(MPI_Comm comm, int const n[], int const Ndims[])
Definition: Distribution.H:138
bool m_debug
Definition: Distribution.H:282
int const (& self_2d_x() const)[3]
Definition: Distribution.H:229
int const (& local_ng_2d_z() const)[3]
Definition: Distribution.H:197
int self_2d_z(int i) const
Definition: Distribution.H:225
MPI_Comm cart_2d_z() const
Definition: Distribution.H:240
Distribution(MPI_Comm comm, int ng, bool debug=false)
Definition: Distribution.H:93
Distribution(MPI_Comm comm, int const n[], int const Ndims[], int *rmap, bool debug=false)
Definition: Distribution.H:105
int self_3d(int i) const
Definition: Distribution.H:226
int const (& local_ng_2d_y() const)[3]
Definition: Distribution.H:196
int const (& global_ng() const)[3]
Definition: Distribution.H:193
distribution_t m_d
Definition: Distribution.H:277
void redistribute_2_to_3(const complex_t *a, complex_t *b, int axis)
Definition: Distribution.H:159
Distribution(MPI_Comm comm, int ng, int const Ndims[], int *rmap, bool debug=false)
Definition: Distribution.H:115
int nproc_2d_z(int i) const
Definition: Distribution.H:208
void redistribute_3_to_2(const complex_t *a, complex_t *b, int axis)
Definition: Distribution.H:163
int local_ng_2d_z(int i) const
Definition: Distribution.H:190
int self_2d_x(int i) const
Definition: Distribution.H:223
int nproc_2d_x(int i) const
Definition: Distribution.H:206
int self_1d(int i) const
Definition: Distribution.H:222
int rank_2d_z(int c[])
Definition: Distribution.H:260
int const (& nproc_3d() const)[3]
Definition: Distribution.H:215
int self_2d_y(int i) const
Definition: Distribution.H:224
size_t local_size() const
Definition: Distribution.H:170
int nproc_3d(int i) const
Definition: Distribution.H:209
int nproc_2d_y(int i) const
Definition: Distribution.H:207
int const (& self_1d() const)[3]
Definition: Distribution.H:228
int rank_2d_y(int c[])
Definition: Distribution.H:254
int const (& nproc_2d_x() const)[3]
Definition: Distribution.H:212
int rank_2d_x(int c[])
Definition: Distribution.H:248
void redistribute_3_to_1(const complex_t *a, complex_t *b)
Definition: Distribution.H:155
int const (& self_2d_y() const)[3]
Definition: Distribution.H:230
int local_ng_2d_x(int i) const
Definition: Distribution.H:188
virtual ~Distribution()
Definition: Distribution.H:130
int const (& nproc_2d_y() const)[3]
Definition: Distribution.H:213
int const (& nproc_2d_z() const)[3]
Definition: Distribution.H:214
double complex complex_t
Definition: complex-type.h:79
void Rank_x_pencils(int *myrank, int coord[], distribution_t *d)
Definition: distribution.c:150
void distribution_3_to_1(const complex_t *a, complex_t *b, distribution_t *d)
Definition: distribution.c:1287
void distribution_fini(distribution_t *d)
Definition: distribution.c:1222
void distribution_3_to_2(const complex_t *a, complex_t *b, distribution_t *d, int z_dim)
Definition: distribution.c:1509
void Coord_y_pencils(int myrank, int coord[], distribution_t *d)
Definition: distribution.c:171
void Rank_y_pencils(int *myrank, int coord[], distribution_t *d)
Definition: distribution.c:189
void distribution_1_to_3(const complex_t *a, complex_t *b, distribution_t *d)
Definition: distribution.c:1269
void Coord_z_pencils(int myrank, int coord[], distribution_t *d)
Definition: distribution.c:206
void Rank_z_pencils(int *myrank, int coord[], distribution_t *d)
Definition: distribution.c:224
void distribution_init(MPI_Comm comm, const int n[], const int Ndims[], distribution_t *d, const int *rmap, bool debug)
Definition: distribution.c:248
void Coord_x_pencils(int myrank, int coord[], distribution_t *d)
Definition: distribution.c:117
void distribution_2_to_3(const complex_t *a, complex_t *b, distribution_t *d, int z_dim)
Definition: distribution.c:1495
AMREX_GPU_HOST_DEVICE Long size(T const &b) noexcept
integer version
Definition: AMReX_GpuRange.H:26
Definition: AlignedAllocator.h:63
Definition: distribution_c.h:93
process_topology_t process_topology_2_y
Definition: distribution_c.h:98
process_topology_t process_topology_1
Definition: distribution_c.h:96
process_topology_t process_topology_2_z
Definition: distribution_c.h:97
process_topology_t process_topology_3
Definition: distribution_c.h:100
int n[3]
Definition: distribution_c.h:95
process_topology_t process_topology_2_x
Definition: distribution_c.h:99
int self[3]
Definition: distribution_c.h:80
int n[3]
Definition: distribution_c.h:81
int nproc[3]
Definition: distribution_c.h:78
MPI_Comm cart
Definition: distribution_c.h:77