BLACSGrid.hpp
Go to the documentation of this file.
1 /*
2  * STRUMPACK -- STRUctured Matrices PACKage, Copyright (c) 2014, The
3  * Regents of the University of California, through Lawrence Berkeley
4  * National Laboratory (subject to receipt of any required approvals
5  * from the U.S. Dept. of Energy). All rights reserved.
6  *
7  * If you have questions about your rights to use or distribute this
8  * software, please contact Berkeley Lab's Technology Transfer
9  * Department at TTD@lbl.gov.
10  *
11  * NOTICE. This software is owned by the U.S. Department of Energy. As
12  * such, the U.S. Government has been granted for itself and others
13  * acting on its behalf a paid-up, nonexclusive, irrevocable,
14  * worldwide license in the Software to reproduce, prepare derivative
15  * works, and perform publicly and display publicly. Beginning five
16  * (5) years after the date permission to assert copyright is obtained
17  * from the U.S. Department of Energy, and subject to any subsequent
18  * five (5) year renewals, the U.S. Government is granted for itself
19  * and others acting on its behalf a paid-up, nonexclusive,
20  * irrevocable, worldwide license in the Software to reproduce,
21  * prepare derivative works, distribute copies to the public, perform
22  * publicly and display publicly, and to permit others to do so.
23  *
24  * Developers: Pieter Ghysels, Francois-Henry Rouet, Xiaoye S. Li.
25  * (Lawrence Berkeley National Lab, Computational Research
26  * Division).
27  */
32 #ifndef BLACS_GRID_HPP
33 #define BLACS_GRID_HPP
34 
35 #include "ScaLAPACKWrapper.hpp"
36 #include "misc/MPIWrapper.hpp"
37 
38 namespace strumpack {
39 
66  class BLACSGrid {
67  public:
72  BLACSGrid() {}
73 
82  BLACSGrid(const MPIComm& comm) : BLACSGrid(comm, comm.size()) { }
83 
92  BLACSGrid(MPIComm&& comm) : BLACSGrid(std::move(comm), comm.size()) { }
93 
106  BLACSGrid(const MPIComm& comm, int P) : comm_(comm), P_(P) { setup(); }
107 
121  BLACSGrid(MPIComm&& comm, int P) : comm_(std::move(comm)), P_(P) { setup(); }
122 
128  if (ctxt_ != -1) scalapack::Cblacs_gridexit(ctxt_);
129  if (ctxt_all_ != -1) scalapack::Cblacs_gridexit(ctxt_all_);
130  if (ctxt_T_ != -1) scalapack::Cblacs_gridexit(ctxt_T_);
131  }
132 
143  BLACSGrid(const BLACSGrid& grid) { *this = grid; }
144 
148  BLACSGrid(BLACSGrid&& grid) { *this = std::move(grid); }
149 
161  BLACSGrid& operator=(const BLACSGrid& grid) {
162  //std::cout << "WARNING copying a BLACS grid is expensive!!" << std::endl;
163  comm_ = grid.Comm();
164  P_ = grid.P();
165  setup();
166  return *this;
167  }
168 
176  comm_ = std::move(grid.comm_);
177  P_ = grid.P_;
178  ctxt_ = grid.ctxt_;
179  ctxt_all_ = grid.ctxt_all_;
180  ctxt_T_ = grid.ctxt_T_;
181  nprows_ = grid.nprows_;
182  npcols_ = grid.npcols_;
183  prow_ = grid.prow_;
184  pcol_ = grid.pcol_;
185  // make sure that grid's context is not destroyed in its
186  // destructor
187  grid.ctxt_ = -1;
188  grid.ctxt_all_ = -1;
189  grid.ctxt_T_ = -1;
190  return *this;
191  }
192 
196  const MPIComm& Comm() const { return comm_; }
197 
201  MPIComm& Comm() { return comm_; }
202 
209  int ctxt() const { return ctxt_; }
210 
220  int ctxt_all() const { return ctxt_all_; }
221 
226  int nprows() const { return nprows_; }
227 
232  int npcols() const { return npcols_; }
233 
238  int prow() const { return prow_; }
239 
244  int pcol() const { return pcol_; }
245 
251  int P() const { return P_; }
252 
257  int npactives() const { return nprows() * npcols(); }
258 
264  bool active() const { return prow_ != -1; }
265 
278  static void layout(int procs, int& proc_rows, int& proc_cols) {
279  // why floor, why not nearest??
280  proc_cols = std::floor(std::sqrt((float)procs));
281  proc_rows = procs / proc_cols;
282  }
283 
293  BLACSGrid g(*this);
294  g.transpose_inplace();
295  return g;
296  }
297 
298  const MPIComm& Comm_active() const {
299  if (active_comm_) return *active_comm_;
300  else return Comm();
301  }
302 
303  private:
304  MPIComm comm_;
305  int P_ = -1;
306  int ctxt_ = -1;
307  int ctxt_all_ = -1;
308  int ctxt_T_ = -1;
309  int nprows_ = -1;
310  int npcols_ = -1;
311  int prow_ = -1;
312  int pcol_ = -1;
313  std::unique_ptr<MPIComm> active_comm_;
314 
315  void setup() {
316  layout(P_, nprows_, npcols_);
317  if (comm_.is_null()) {
318  ctxt_ = ctxt_all_ = ctxt_T_ = -1;
319  prow_ = pcol_ = -1;
320  } else {
321  int active_procs = nprows_ * npcols_;
322  if (active_procs < P_) {
323  active_comm_.reset(new MPIComm(comm_.sub(0, active_procs)));
324  if (comm_.rank() < active_procs) {
325  ctxt_ = scalapack::Csys2blacs_handle(active_comm_->comm());
326  scalapack::Cblacs_gridinit(&ctxt_, "C", nprows_, npcols_);
327  ctxt_T_ = scalapack::Csys2blacs_handle(active_comm_->comm());
328  scalapack::Cblacs_gridinit(&ctxt_T_, "R", npcols_, nprows_);
329  } else ctxt_ = ctxt_T_ = -1;
330  } else {
331  ctxt_ = scalapack::Csys2blacs_handle(comm_.comm());
332  scalapack::Cblacs_gridinit(&ctxt_, "C", nprows_, npcols_);
333  ctxt_T_ = scalapack::Csys2blacs_handle(comm_.comm());
334  scalapack::Cblacs_gridinit(&ctxt_T_, "R", npcols_, nprows_);
335  }
336  ctxt_all_ = scalapack::Csys2blacs_handle(comm_.comm());
337  scalapack::Cblacs_gridinit(&ctxt_all_, "R", 1, P_);
338  int dummy1, dummy2;
339  scalapack::Cblacs_gridinfo(ctxt_, &dummy1, &dummy2, &prow_, &pcol_);
340  }
341  }
342 
343  void transpose_inplace() {
344  std::swap(ctxt_, ctxt_T_);
345  std::swap(nprows_, npcols_);
346  std::swap(prow_, pcol_);
347  }
348 
349  friend std::ostream& operator<<(std::ostream& os, const BLACSGrid* g);
350  };
351 
352 
357  inline std::ostream& operator<<(std::ostream& os, const BLACSGrid* g) {
358  if (!g) os << "null";
359  else
360  os << " ctxt[" << g->ctxt()
361  << "](" << g->nprows() << "x" << g->npcols() << " +"
362  << (g->P()-g->npactives()) << ")ctxtT[" << g->ctxt_T_ << "]";
363  return os;
364  }
365 
366 } // end namespace strumpack
367 
368 #endif // BLACS_GRID_HPP
Contains some simple C++ MPI wrapper utilities.
This is a small wrapper class around a BLACS grid and a BLACS context.
Definition: BLACSGrid.hpp:66
bool active() const
Definition: BLACSGrid.hpp:264
~BLACSGrid()
Definition: BLACSGrid.hpp:127
BLACSGrid(const MPIComm &comm)
Definition: BLACSGrid.hpp:82
BLACSGrid()
Definition: BLACSGrid.hpp:72
friend std::ostream & operator<<(std::ostream &os, const BLACSGrid *g)
Definition: BLACSGrid.hpp:357
BLACSGrid transpose() const
Definition: BLACSGrid.hpp:292
BLACSGrid(const MPIComm &comm, int P)
Definition: BLACSGrid.hpp:106
static void layout(int procs, int &proc_rows, int &proc_cols)
Definition: BLACSGrid.hpp:278
int npcols() const
Definition: BLACSGrid.hpp:232
int ctxt_all() const
Definition: BLACSGrid.hpp:220
int npactives() const
Definition: BLACSGrid.hpp:257
int P() const
Definition: BLACSGrid.hpp:251
int pcol() const
Definition: BLACSGrid.hpp:244
BLACSGrid & operator=(const BLACSGrid &grid)
Definition: BLACSGrid.hpp:161
BLACSGrid(MPIComm &&comm)
Definition: BLACSGrid.hpp:92
BLACSGrid(MPIComm &&comm, int P)
Definition: BLACSGrid.hpp:121
BLACSGrid(const BLACSGrid &grid)
Definition: BLACSGrid.hpp:143
const MPIComm & Comm() const
Definition: BLACSGrid.hpp:196
BLACSGrid & operator=(BLACSGrid &&grid)
Definition: BLACSGrid.hpp:175
int nprows() const
Definition: BLACSGrid.hpp:226
MPIComm & Comm()
Definition: BLACSGrid.hpp:201
BLACSGrid(BLACSGrid &&grid)
Definition: BLACSGrid.hpp:148
int ctxt() const
Definition: BLACSGrid.hpp:209
int prow() const
Definition: BLACSGrid.hpp:238
Wrapper class around an MPI_Comm object.
Definition: MPIWrapper.hpp:194
Definition: StrumpackOptions.hpp:43