Teuchos Package Browser (Single Doxygen Collection)  Version of the Day
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
DefaultMpiComm_UnitTests.cpp
Go to the documentation of this file.
1 // @HEADER
2 // *****************************************************************************
3 // Teuchos: Common Tools Package
4 //
5 // Copyright 2004 NTESS and the Teuchos contributors.
6 // SPDX-License-Identifier: BSD-3-Clause
7 // *****************************************************************************
8 // @HEADER
9 
11 
12 
14 #include "Teuchos_CommHelpers.hpp"
15 #include "Teuchos_DefaultComm.hpp"
17 #include "Teuchos_getConst.hpp"
18 #include "Teuchos_as.hpp"
19 
20 #ifdef HAVE_TEUCHOS_MPI
22 #endif
23 
24 #ifdef HAVE_TEUCHOS_QD
25 # include <qd/dd_real.h>
26 #endif
27 
28 namespace std {
29 
30 
31 template <typename Packet>
32 ostream & operator<< ( ostream& os, const pair<Packet, Packet>& arg)
33 {
34  os << "(" << arg.first << "," << arg.second << ")";
35  return os;
36 }
37 
38 
39 } // namespace std
40 
41 
42 namespace Teuchos {
43 
44 
45 template<typename Packet>
46 struct ScalarTraits<std::pair<Packet,Packet> >
47 {
49  typedef std::pair<typename PST::magnitudeType, typename PST::magnitudeType> magnitudeType;
50  static const bool isComplex = PST::isComplex;
51  static const bool isComparable = PST::isComparable;
52  static const bool hasMachineParameters = PST::hasMachineParameters;
53  // Not defined: eps(), sfmin(), base(), prec(), t(), rnd(), emin(), rmin(), emax(), rmax()
54  static inline magnitudeType magnitude(std::pair<Packet,Packet> a) { return std::pair<Packet,Packet>( PST::magnitude(a.first), PST::magnitude(a.second) ); }
55  static inline std::pair<Packet,Packet> zero() { return std::pair<Packet,Packet>(PST::zero(),PST::zero()); }
56  static inline std::pair<Packet,Packet> one() { return std::pair<Packet,Packet>(PST::one(), PST::one()); }
57  static inline std::pair<Packet,Packet> conjugate(std::pair<Packet,Packet> x) { return std::pair<Packet,Packet>(PST::conjugate(x.first), PST::conjugate(x.second) ); }
58  static inline std::pair<Packet,Packet> real(std::pair<Packet,Packet> x) { return std::pair<Packet,Packet>(PST::real(x.first), PST::real(x.second) ); }
59  static inline std::pair<Packet,Packet> imag(std::pair<Packet,Packet> x) { return std::pair<Packet,Packet>(PST::imag(x.first), PST::imag(x.second) ); }
60  static inline bool isnaninf(std::pair<Packet,Packet> x) { return PST::isnaninf(x.first) || PST::isnaninf(x.second); }
61  static inline void seedrandom(unsigned int s) { PST::seedrandom(s); }
62  static inline std::pair<Packet,Packet> random() { return std::pair<Packet,Packet>( PST::random(), PST::random() ); }
63  static inline std::string name() { return "std::pair<" + Teuchos::TypeNameTraits<Packet>::name() + "," + Teuchos::TypeNameTraits<Packet>::name() + ">"; }
64  static inline std::pair<Packet,Packet> squareroot(std::pair<Packet,Packet> x) { return std::pair<Packet,Packet>(PST::squareroot(x.first), PST::squareroot(x.second)); }
65  static inline std::pair<Packet,Packet> pow(std::pair<Packet,Packet> x, std::pair<Packet,Packet> y) { return std::pair<Packet,Packet>( PST::pow(x.first,y.first), PST::pow(x.second,y.second) ); }
66 };
67 
68 template<class Packet, class ConvertToPacket>
69 class ValueTypeConversionTraits<std::pair<Packet,Packet>, ConvertToPacket> {
70 public:
71  static std::pair<Packet,Packet> convert( const ConvertToPacket t )
72  {
73  return std::pair<Packet,Packet>(t,t);
74  }
75  static std::pair<Packet,Packet> safeConvert( const ConvertToPacket t )
76  {
77  return std::pair<Packet,Packet>(t,t);
78  }
79 };
80 
81 
82 } // namespace Teuchos
83 
84 
85 namespace {
86 
87 
88 using Teuchos::as;
89 using Teuchos::RCP;
90 using Teuchos::rcp;
91 using Teuchos::Array;
92 using Teuchos::Comm;
96 using Teuchos::outArg;
97 
98 
99 bool testMpi = true;
100 
101 
102 double errorTolSlack = 1e+1;
103 
104 
105 
107 {
108 
110 
111  clp.addOutputSetupOptions(true);
112 
113  clp.setOption(
114  "test-mpi", "test-serial", &testMpi,
115  "Test MPI (if available) or force test of serial. In a serial build,"
116  " this option is ignored and a serial comm is always used." );
117 
118  clp.setOption(
119  "error-tol-slack", &errorTolSlack,
120  "Slack off of machine epsilon used to check test results" );
121 
122 }
123 
124 
125 template<class Ordinal>
126 RCP<const Comm<Ordinal> > getDefaultComm()
127 {
128  if (testMpi) {
129  return DefaultComm<Ordinal>::getComm();
130  }
131  return rcp(new Teuchos::SerialComm<Ordinal>);
132 }
133 
134 
135 TEUCHOS_UNIT_TEST_TEMPLATE_1_DECL( DefaultMpiComm, basic, Ordinal )
136 {
137  RCP<const Comm<Ordinal> > comm = getDefaultComm<Ordinal>();
138  out << "comm = " << Teuchos::describe(*comm);
139  TEST_EQUALITY( size(*comm), GlobalMPISession::getNProc() );
140 }
141 
142 
143 #ifdef HAVE_TEUCHOS_MPI
144 
145 
146 TEUCHOS_UNIT_TEST( DefaultMpiComm, getRawMpiComm )
147 {
148  ECHO(MPI_Comm rawMpiComm = MPI_COMM_WORLD);
149  ECHO(const RCP<const Comm<int> > comm =
150  Teuchos::createMpiComm<int>(Teuchos::opaqueWrapper(rawMpiComm)));
151  out << "comm = " << Teuchos::describe(*comm);
152  ECHO(MPI_Comm rawMpiComm2 = Teuchos::getRawMpiComm<int>(*comm));
153  TEST_EQUALITY( rawMpiComm2, rawMpiComm );
154 }
155 
156 
157 TEUCHOS_UNIT_TEST( DefaultMpiComm, getRawMpiCommWithTag )
158 {
159  ECHO(MPI_Comm rawMpiComm = MPI_COMM_WORLD);
160  ECHO(const RCP<const Comm<int> > comm =
161  Teuchos::createMpiComm<int>(Teuchos::opaqueWrapper(rawMpiComm), 123));
162  out << "comm = " << Teuchos::describe(*comm);
163  ECHO(MPI_Comm rawMpiComm2 = Teuchos::getRawMpiComm<int>(*comm));
164  TEST_EQUALITY( rawMpiComm2, rawMpiComm );
165  TEST_EQUALITY( comm->getTag(), 123);
166 }
167 
168 
169 #endif // HAVE_TEUCHOS_MPI
170 
171 
172 TEUCHOS_UNIT_TEST_TEMPLATE_2_DECL( DefaultMpiComm, ReadySend1, Ordinal, Packet )
173 {
174 
175  using Teuchos::broadcast;
176  using Teuchos::readySend;
177  using Teuchos::wait;
178  using Teuchos::as;
179  using Teuchos::rcpFromRef;
180  using Teuchos::outArg;
181  using Teuchos::isend;
182  using Teuchos::ireceive;
183  using Teuchos::wait;
184  using Teuchos::SerialComm;
185  using Teuchos::is_null;
186  using Teuchos::arcp;
187  using Teuchos::arcpClone;
188  using Teuchos::rcp_dynamic_cast;
189  using Teuchos::ArrayRCP;
190  using Teuchos::ptr;
192  //typedef typename PT::magnitudeType PacketMag; // unused
193  //typedef Teuchos::ScalarTraits<PacketMag> PMT; // unused
194 
195  RCP<const Comm<Ordinal> > comm = getDefaultComm<Ordinal>();
196  const Ordinal numProcs = size(*comm);
197  const Ordinal procRank = rank(*comm);
198 
199  if (
200  numProcs == 1
201  &&
202  !is_null(rcp_dynamic_cast<const SerialComm<Ordinal> >(comm))
203  )
204  {
205  out << "\nThis is Teuchos::SerialComm which does not support readySend!\n";
206  return; // Pass!
207  }
208 
209  PT::seedrandom(as<unsigned int>(procRank));
210  Packet origSendData = PT::random();
211  Packet origRecvData = PT::random();
212  broadcast<Ordinal, Packet>( *comm, 0, outArg(origSendData) );
213 
214  Packet sendData = origSendData;
215  Packet recvData = origRecvData;
216 
217  RCP<Teuchos::CommRequest<Ordinal> > recvRequest;
218 
219  // Post non-block receive on proc 0
220  if (procRank == 0) {
221  // Post non-blocking receive from proc n-1
222  recvRequest = ireceive<Ordinal, Packet>(
223  *comm,
224  rcp(&recvData,false),
225  numProcs-1
226  );
227  }
228  barrier(*comm);
229 
230  if (procRank == numProcs-1) {
231  // ready send from proc n-1 to proc 0
232  // send data in sendData
233  readySend<Ordinal, Packet>(
234  *comm,
235  sendData,
236  0
237  );
238  }
239  barrier(*comm);
240 
241  if (procRank == 0) {
242  // wait for request on 0
243  wait( *comm, outArg(recvRequest) );
244  }
245  barrier(*comm);
246 
247  // test that all procs have recvRequest == Teuchos::null
248  TEST_EQUALITY_CONST( recvRequest, Teuchos::null );
249 
250  // proc 0 should have recvData == sendData
251  if (procRank == 0) {
252  TEST_EQUALITY( recvData, sendData );
253  }
254  // other procs should have recvData == origRecvData (i.e., unchanged)
255  else {
256  TEST_EQUALITY( recvData, origRecvData );
257  }
258  // all procs should have sendData == origSendData
259  TEST_EQUALITY( sendData, origSendData );
260 
261  // All procs fail if any proc fails
262  int globalSuccess_int = -1;
263  reduceAll( *comm, Teuchos::REDUCE_SUM, success ? 0 : 1, outArg(globalSuccess_int) );
264  TEST_EQUALITY_CONST( globalSuccess_int, 0 );
265 }
266 
267 
268 TEUCHOS_UNIT_TEST_TEMPLATE_2_DECL( DefaultMpiComm, ReadySend, Ordinal, Packet )
269 {
270 
271  using Teuchos::broadcast;
272  using Teuchos::readySend;
273  using Teuchos::wait;
274  using Teuchos::as;
275  using Teuchos::rcpFromRef;
276  using Teuchos::outArg;
277  using Teuchos::isend;
278  using Teuchos::ireceive;
279  using Teuchos::wait;
280  using Teuchos::SerialComm;
281  using Teuchos::is_null;
282  using Teuchos::arcp;
283  using Teuchos::arcpClone;
284  using Teuchos::rcp_dynamic_cast;
285  using Teuchos::ArrayRCP;
287  //typedef typename PT::magnitudeType PacketMag; // unused
288  //typedef Teuchos::ScalarTraits<PacketMag> PMT; // unused
289 
290  RCP<const Comm<Ordinal> > comm = getDefaultComm<Ordinal>();
291  const Ordinal numProcs = size(*comm);
292  const Ordinal procRank = rank(*comm);
293 
294  if (
295  numProcs == 1
296  &&
297  !is_null(rcp_dynamic_cast<const SerialComm<Ordinal> >(comm))
298  )
299  {
300  out << "\nThis is Teuchos::SerialComm which does not support readySend!\n";
301  return; // Pass!
302  }
303 
304  const int dataLen = 3;
305 
306  const ArrayRCP<Packet> origSendData = arcp<Packet>(dataLen);
307  const ArrayRCP<Packet> origRecvData = arcp<Packet>(dataLen);
308  PT::seedrandom(as<unsigned int>(procRank));
309  for (int j = 0; j < dataLen; ++j) {
310  origSendData[j] = PT::random();
311  origRecvData[j] = PT::random();
312  }
313  broadcast<Ordinal, Packet>( *comm, 0, origSendData() );
314 
315  const ArrayRCP<Packet> sendData = arcpClone<Packet>(origSendData());
316  const ArrayRCP<Packet> recvData = arcpClone<Packet>(origRecvData());
317 
318  RCP<Teuchos::CommRequest<Ordinal> > recvRequest;
319 
320  // both proc 0 and proc n-1 will post non-block receives, into recvData
321  // then proc 0 will initiate a ready-send to proc n-1; the latter will initiate a wait
322  // a barrier
323  // then proc n-1 will initiate a ready-send to proc 0 of the data from recvData; the latter will initiate a wait
324  // a barrier
325  // now both of these procs should have matching data in sendData and recvData
326 
327  // Post non-block receive on both procs
328  if (procRank == 0) {
329  // Post non-blocking receive from proc n-1
330  recvRequest = ireceive<Ordinal, Packet>(
331  *comm,
332  recvData.persistingView(0, dataLen),
333  numProcs-1
334  );
335  }
336  else if (procRank == numProcs-1) {
337  // Post non-blocking receive from proc 0
338  recvRequest = ireceive<Ordinal, Packet>(
339  *comm,
340  recvData.persistingView(0, dataLen),
341  0
342  );
343  }
344  barrier(*comm);
345 
346  if (procRank == 0) {
347  // ready send from proc 0 to proc n-1
348  // send data in sendData
349  readySend<Ordinal, Packet>(
350  *comm,
351  sendData(),
352  numProcs-1
353  );
354  }
355  else if (procRank == numProcs-1) {
356  // wait for request on proc n-1
357  wait( *comm, outArg(recvRequest) );
358  }
359  barrier(*comm);
360 
361  if (procRank == 0) {
362  // wait for request on 0
363  wait( *comm, outArg(recvRequest) );
364  }
365  else if (procRank == numProcs-1) {
366  // ready send from proc n-1 to proc 0
367  // send data in recvData: THIS IS IMPORTANT: SEE ABOVE
368  readySend<Ordinal, Packet>(
369  *comm,
370  recvData(),
371  0
372  );
373  }
374  barrier(*comm);
375 
376  // test that all procs (even non-participating) have recvRequest == Teuchos::null
377  TEST_EQUALITY_CONST( recvRequest, Teuchos::null );
378 
379  // participating procs should have recvData == sendData
380  if (procRank == 0 || procRank == numProcs-1) {
381  TEST_COMPARE_ARRAYS( recvData, sendData );
382  }
383  // non-participating procs should have recvData == origRecvData (i.e., unchanged)
384  else {
385  TEST_COMPARE_ARRAYS( recvData, origRecvData );
386  }
387  // all procs should have sendData == origSendData
388  TEST_COMPARE_ARRAYS( sendData, origSendData );
389 
390  // All procs fail if any proc fails
391  int globalSuccess_int = -1;
392  reduceAll( *comm, Teuchos::REDUCE_SUM, success ? 0 : 1, outArg(globalSuccess_int) );
393  TEST_EQUALITY_CONST( globalSuccess_int, 0 );
394 }
395 
396 
397 TEUCHOS_UNIT_TEST_TEMPLATE_2_DECL( DefaultMpiComm, NonblockingSendReceive, Ordinal, Packet )
398 {
399  using Teuchos::as;
400  using Teuchos::rcpFromRef;
401  using Teuchos::outArg;
402  using Teuchos::isend;
403  using Teuchos::ireceive;
404  using Teuchos::wait;
405  using Teuchos::SerialComm;
406  using Teuchos::rcp_dynamic_cast;
407  using std::endl;
409 
410  RCP<const Comm<Ordinal> > comm = getDefaultComm<Ordinal>();
411  const Ordinal numProcs = size(*comm);
412  const Ordinal procRank = rank(*comm);
413 
414  if (
415  numProcs == 1
416  &&
417  !is_null(rcp_dynamic_cast<const SerialComm<Ordinal> >(comm))
418  )
419  {
420  out << "\nThis is Teuchos::SerialComm which does not yet support isend/ireceive!\n";
421  return; // Pass!
422  }
423 
424  // Only use randomize on one proc and then broadcast
425  Packet orig_input_data = PT::random();
426  broadcast( *comm, 0, &orig_input_data );
427 
428  const Packet orig_output_data = as<Packet>(-1);
429 
430  const Packet input_data = orig_input_data;
431  Packet output_data = orig_output_data;
432 
433  RCP<Teuchos::CommRequest<Ordinal> > recvRequest;
434  RCP<Teuchos::CommRequest<Ordinal> > sendRequest;
435 
436  out << "Exchanging messages" << endl;
437 
438  if (procRank == 0) {
439  // Create copy of data to make sure that persisting relationship is
440  // maintained!
441  sendRequest = isend<Ordinal, Packet>(
442  *comm, Teuchos::rcp(new Packet(input_data)), numProcs-1);
443  }
444  if (procRank == numProcs-1) {
445  // We will need to read output_data after wait(...) below
446  recvRequest = ireceive<Ordinal, Packet>(
447  *comm, rcpFromRef(output_data), 0);
448  }
449 
450  out << "Waiting for messages" << endl;
451 
452  if (procRank == 0) {
453  wait( *comm, outArg(sendRequest) );
454  }
455  if (procRank == numProcs-1) {
456  wait( *comm, outArg(recvRequest) );
457  }
458 
459  TEST_EQUALITY_CONST( sendRequest, Teuchos::null );
460  TEST_EQUALITY_CONST( recvRequest, Teuchos::null );
461 
462  out << "Testing message correctness" << endl;
463 
464  if (procRank == numProcs-1) {
465  TEST_EQUALITY( output_data, input_data );
466  }
467  else {
468  TEST_EQUALITY( output_data, orig_output_data );
469  }
470  TEST_EQUALITY( input_data, orig_input_data );
471 
472  // All procs fail if any proc fails
473  int globalSuccess_int = -1;
474  reduceAll( *comm, Teuchos::REDUCE_SUM, success ? 0 : 1, outArg(globalSuccess_int) );
475  TEST_EQUALITY_CONST( globalSuccess_int, 0 );
476 }
477 
478 
479 TEUCHOS_UNIT_TEST_TEMPLATE_2_DECL( DefaultMpiComm, NonblockingSendReceive_isReady_true, Ordinal, Packet )
480 {
481  using Teuchos::as;
482  using Teuchos::rcpFromRef;
483  using Teuchos::outArg;
484  using Teuchos::isend;
485  using Teuchos::ireceive;
486  using Teuchos::SerialComm;
487  using Teuchos::rcp_dynamic_cast;
489 
490  RCP<const Comm<Ordinal>> comm = getDefaultComm<Ordinal>();
491  const Ordinal numProcs = size(*comm);
492  const Ordinal procRank = rank(*comm);
493 
494  if (numProcs == 1 && !is_null(rcp_dynamic_cast<const SerialComm<Ordinal>>(comm))) {
495  out << "\nThis is Teuchos::SerialComm which does not yet support isend/ireceive!\n";
496  return;
497  }
498 
499  // Only use randomize on one proc and then broadcast
500  Packet input_data = PT::random();
501  broadcast(*comm, 0, &input_data);
502  Packet output_data = as<Packet>(-1);
503 
504  const Ordinal sendRank = (procRank + 1) % numProcs;
505  const Ordinal recvRank = (procRank + numProcs - 1) % numProcs;
506 
507  RCP<Teuchos::CommRequest<Ordinal>> recvRequest = ireceive<Ordinal, Packet>(*comm, rcpFromRef(output_data), recvRank);
508  RCP<Teuchos::CommRequest<Ordinal>> sendRequest = isend<Ordinal, Packet>(*comm, rcpFromRef(input_data), sendRank);
509 
510  recvRequest->wait();
511  TEST_ASSERT(recvRequest->isReady());
512 
513  // All procs fail if any proc fails
514  int globalSuccess_int = -1;
515  reduceAll(*comm, Teuchos::REDUCE_SUM, success ? 0 : 1, outArg(globalSuccess_int));
516  TEST_EQUALITY_CONST(globalSuccess_int, 0);
517 }
518 
519 
520 TEUCHOS_UNIT_TEST_TEMPLATE_2_DECL( DefaultMpiComm, NonblockingSendReceive_isReady_false, Ordinal, Packet )
521 {
522  using Teuchos::as;
523  using Teuchos::rcpFromRef;
524  using Teuchos::outArg;
525  using Teuchos::ireceive;
526  using Teuchos::SerialComm;
527  using Teuchos::rcp_dynamic_cast;
528 
529  RCP<const Comm<Ordinal>> comm = getDefaultComm<Ordinal>();
530  const Ordinal numProcs = size(*comm);
531  const Ordinal procRank = rank(*comm);
532 
533  if (numProcs == 1 && !is_null(rcp_dynamic_cast<const SerialComm<Ordinal>>(comm))) {
534  out << "\nThis is Teuchos::SerialComm which does not yet support isend/ireceive!\n";
535  return;
536  }
537 
538  Packet output_data = as<Packet>(-1);
539 
540  RCP<Teuchos::CommRequest<Ordinal>> recvRequest;
541  const Ordinal recvRank = (procRank + numProcs - 1) % numProcs;
542 
543  recvRequest = ireceive<Ordinal, Packet>(*comm, rcpFromRef(output_data), recvRank);
544  TEST_ASSERT(!recvRequest->isReady());
545 
546  // All procs fail if any proc fails
547  int globalSuccess_int = -1;
548  reduceAll(*comm, Teuchos::REDUCE_SUM, success ? 0 : 1, outArg(globalSuccess_int));
549  TEST_EQUALITY_CONST(globalSuccess_int, 0);
550 }
551 
552 
553 template <class Ordinal>
554 bool null_request_is_always_ready_if_mpi_available() {
555 #ifdef HAVE_TEUCHOS_MPI
556  Teuchos::MpiCommRequestBase<Ordinal> nullRequest;
557  return nullRequest.isReady();
558 #else
559  return true;
560 #endif
561 }
562 
563 TEUCHOS_UNIT_TEST_TEMPLATE_2_DECL( DefaultMpiComm, NonblockingSendReceive_isReady_nullIsTrue, Ordinal, Packet )
564 {
565  using Teuchos::outArg;
566 
567  RCP<const Comm<Ordinal>> comm = getDefaultComm<Ordinal>();
568  TEST_ASSERT(null_request_is_always_ready_if_mpi_available<Ordinal>());
569 
570  // All procs fail if any proc fails
571  int globalSuccess_int = -1;
572  reduceAll(*comm, Teuchos::REDUCE_SUM, success ? 0 : 1, outArg(globalSuccess_int));
573  TEST_EQUALITY_CONST(globalSuccess_int, 0);
574 }
575 
576 
577 TEUCHOS_UNIT_TEST_TEMPLATE_2_DECL( DefaultMpiComm, NonblockingSendReceiveSet, Ordinal, Packet )
578 {
579  using Teuchos::as;
580  using Teuchos::rcpFromRef;
581  using Teuchos::outArg;
582  using Teuchos::arcp;
583  using Teuchos::arcpClone;
584  using Teuchos::ArrayRCP;
585  using Teuchos::isend;
586  using Teuchos::ireceive;
587  using Teuchos::wait;
588  using Teuchos::broadcast;
589  using Teuchos::SerialComm;
590  using Teuchos::rcp_dynamic_cast;
591  using std::endl;
593  //typedef typename PT::magnitudeType PacketMag; // unused
594  //typedef Teuchos::ScalarTraits<PacketMag> PMT; // unused
595 
596  RCP<const Comm<Ordinal> > comm = getDefaultComm<Ordinal>();
597  const Ordinal numProcs = size(*comm);
598  const Ordinal procRank = rank(*comm);
599 
600  if (
601  numProcs == 1
602  &&
603  !is_null(rcp_dynamic_cast<const SerialComm<Ordinal> >(comm))
604  )
605  {
606  out << "\nThis is Teuchos::SerialComm which does not yet support isend/ireceive!\n";
607  return; // Pass!
608  }
609 
610  const int numSendRecv = 4;
611  const int sendLen = 3;
612 
613  out << "Creating data" << endl;
614 
615  const ArrayRCP<Packet> origInputData = arcp<Packet>(numSendRecv*sendLen);
616  const ArrayRCP<Packet> origOutputData = arcp<Packet>(numSendRecv*sendLen);
617  {
618  int offset = 0;
619  for (int i = 0; i < numSendRecv; ++i, offset += sendLen) {
620  const ArrayRCP<Packet> origInputData_i =
621  origInputData.persistingView(offset, sendLen);
622  const ArrayRCP<Packet> origOutputData_i =
623  origOutputData.persistingView(offset, sendLen);
624  for (int j = 0; j < sendLen; ++j) {
625  origInputData_i[j] = PT::random();
626  origOutputData_i[j] = PT::random();
627  }
628  }
629  }
630  out << "Broadcasting data" << endl;
631  broadcast<Ordinal, Packet>( *comm, 0, origInputData() );
632 
633  const ArrayRCP<Packet> inputData = arcpClone<Packet>(origInputData());
634  const ArrayRCP<Packet> outputData = arcpClone<Packet>(origOutputData());
635 
636  Array<RCP<Teuchos::CommRequest<Ordinal> > > recvRequests;
637  Array<RCP<Teuchos::CommRequest<Ordinal> > > sendRequests;
638 
639  out << "Exchanging data" << endl;
640 
641  // Send from proc 0 to proc numProcs-1
642  if (procRank == 0) {
643  // Create copy of data to make sure that persisting relationship is
644  // maintained!
645  int offset = 0;
646  for (int i = 0; i < numSendRecv; ++i, offset += sendLen) {
647  sendRequests.push_back(
648  isend<Ordinal, Packet>(
649  *comm,
650  arcpClone<Packet>(inputData(offset, sendLen)),
651  numProcs-1
652  )
653  );
654  }
655  }
656 
657  // Receive from proc 0 on proc numProcs-1
658  if (procRank == numProcs-1) {
659  // We will need to read output_data after wait(...) below
660  int offset = 0;
661  for (int i = 0; i < numSendRecv; ++i, offset += sendLen) {
662  recvRequests.push_back(
663  ireceive<Ordinal, Packet>(
664  *comm, outputData.persistingView(offset, sendLen), 0
665  )
666  );
667  }
668  }
669 
670  out << "Waiting on messages" << endl;
671 
672  if (procRank == 0) {
673  waitAll( *comm, sendRequests() );
674  }
675  if (procRank == numProcs-1) {
676  waitAll( *comm, recvRequests() );
677  }
678 
679  out << "Testing received data" << endl;
680 
681  if (!sendRequests.empty()) {
682  for (int i = 0; i < numSendRecv; ++i) {
683  TEST_EQUALITY_CONST( sendRequests[i], Teuchos::null );
684  }
685  }
686 
687  if (!recvRequests.empty()) {
688  for (int i = 0; i < numSendRecv; ++i) {
689  TEST_EQUALITY_CONST( recvRequests[i], Teuchos::null );
690  }
691  }
692  // ToDo: Write a test macro for this in one shot!
693 
694  if (procRank == numProcs-1) {
695  TEST_COMPARE_ARRAYS( outputData, inputData );
696  }
697  else {
698  TEST_COMPARE_ARRAYS( outputData, origOutputData );
699  }
700  TEST_COMPARE_ARRAYS( inputData, origInputData );
701 
702  // All procs fail if any proc fails
703  int globalSuccess_int = -1;
704  reduceAll( *comm, Teuchos::REDUCE_SUM, success ? 0 : 1, outArg(globalSuccess_int) );
705  TEST_EQUALITY_CONST( globalSuccess_int, 0 );
706 
707 }
708 
709 TEUCHOS_UNIT_TEST_TEMPLATE_1_DECL(DefaultMpiComm, duplicate, Ordinal)
710 {
711  RCP< const Comm<Ordinal> > comm = getDefaultComm<Ordinal>();
712  int initialRank = comm->getRank();
713  int initialSize = comm->getSize();
714 
715  RCP< const Comm<Ordinal> > newComm = comm->duplicate();
716  TEST_EQUALITY(newComm->getSize(), initialSize);
717  TEST_EQUALITY(newComm->getRank(), initialRank);
718 
719  // TODO Make sure the communication space is distinct.
720 }
721 
722 TEUCHOS_UNIT_TEST_TEMPLATE_1_DECL(DefaultMpiComm, split, Ordinal) {
723  RCP< const Comm<Ordinal> > comm = getDefaultComm<Ordinal>();
724  int initialRank = comm->getRank();
725  int initialSize = comm->getSize();
726 
727  // Partition this communicator into two: one with the odd ranks and one with
728  // the even ones. Pass a common key for everyone to maintain the same
729  // ordering as in the initial communicator.
730  RCP< const Comm<Ordinal> > newComm = comm->split(initialRank % 2, 0);
731 
732  // Check the size of the new communicator and my rank within it.
733  int halfSize = initialSize / 2;
734  int newSize = newComm->getSize();
735  int newRank = newComm->getRank();
736  if (initialSize % 2 == 0) {
737  TEST_EQUALITY(newSize, halfSize);
738  }
739  else {
740  TEST_EQUALITY(newSize, initialRank % 2 == 0 ? halfSize + 1 : halfSize);
741  }
742  TEST_EQUALITY(newRank, initialRank / 2);
743 
744  // Negative color values get a null communicator.
745  RCP< const Comm<Ordinal> > shouldBeNull = comm->split(-1, 0);
746  TEST_ASSERT(shouldBeNull.is_null());
747 }
748 
749 
750 namespace {
751 
752 
753 template<typename ValueType>
754 class MonotoneSequence
755 {
756  ValueType currentValue_;
757 public:
758  typedef ValueType value_type;
759 
760  MonotoneSequence(const value_type& initialValue) : currentValue_(initialValue)
761  {}
762 
763  value_type operator()()
764  {
765  return currentValue_++;
766  }
767 };
768 
769 
770 } // namepsace
771 
772 
773 TEUCHOS_UNIT_TEST_TEMPLATE_1_DECL(DefaultMpiComm, createSubcommunicator, Ordinal) {
774  RCP< const Comm<Ordinal> > comm = getDefaultComm<Ordinal>();
775  int initialRank = comm->getRank();
776  int initialSize = comm->getSize();
777 
778  // Create a new communicator that reverses all of the ranks.
779  std::vector< int > ranks(initialSize);
780  std::generate(ranks.begin(), ranks.end(), MonotoneSequence<int>(0));
781  std::reverse(ranks.begin(), ranks.end());
782  RCP< const Comm<Ordinal> > newComm = comm->createSubcommunicator(ranks);
783  TEST_EQUALITY(newComm->getSize(), initialSize);
784  int expectedNewRank = initialSize - initialRank - 1;
785  TEST_EQUALITY(newComm->getRank(), expectedNewRank);
786 
787  // Processes that aren't in the group get a null communicator.
788  std::vector<int> rank0Only(1, 0);
789  RCP< const Comm<Ordinal> > rank0Comm = comm->createSubcommunicator(rank0Only);
790  // Original rank 0 should be valid, all others should be null.
791  if (initialRank == 0) {
792  TEST_ASSERT(rank0Comm.is_valid_ptr());
793  } else {
794  TEST_ASSERT(rank0Comm.is_null());
795  }
796 }
797 
798 
799 #ifdef HAVE_TEUCHOS_MPI
800 
801 
802 TEUCHOS_UNIT_TEST(DefaultMpiComm, TagConsistency )
803 {
804  using Teuchos::tuple; using Teuchos::inoutArg;
805 
806  const Teuchos::RCP<const Teuchos::Comm<int> > defaultComm =
808  const int comm_size = defaultComm->getSize();
809  const int comm_rank = defaultComm->getRank();
810 
811  // Must have at least two processes to run this test!
812  if (comm_size < 2) {
813  return;
814  }
815 
816  // Create a subcomm that contains just two processes
817  const Teuchos::RCP<const Teuchos::Comm<int> > masterComm =
818  defaultComm->createSubcommunicator(tuple<int>(0, 1)());
819 
820  if (comm_rank <= 1) {
821 
822  const int masterComm_size = masterComm->getSize();
823  (void) masterComm_size; // Forestall "unused variable" warning.
824  const int masterComm_rank = masterComm->getRank();
825 
826  // Split the main communicator into 2 overlapping groups
828  masterComm->createSubcommunicator(tuple<int>(0, 1)());
830  masterComm->createSubcommunicator(tuple<int>(0)());
831 
832  // Create another communicator.
834  masterComm->createSubcommunicator(tuple<int>(0, 1)());
835 
836  // Get my mpi tag for comm 3.
837  int my_tag = Teuchos::rcp_dynamic_cast<const Teuchos::MpiComm<int> >(
838  comm_3 )->getTag();
839 
840  // Collect the tags for comm 3.
841  int tag1 = 0;
842  if (masterComm_rank == 0) { tag1 = my_tag; }
843  masterComm->barrier();
844  Teuchos::broadcast( *masterComm, 0, inoutArg(tag1) );
845 
846  int tag2 = 0;
847  if (masterComm_rank == 1) { tag2 = my_tag; }
848  masterComm->barrier();
849  Teuchos::broadcast( *masterComm, 1, inoutArg(tag2) );
850 
851  // This currently fails.
852  TEST_EQUALITY( tag1, tag2 );
853 
854  }
855 
856 }
857 
858 
859 #endif // HAVE_TEUCHOS_MPI
860 
861 
862 //
863 // Instantiations
864 //
865 
866 
867 #ifdef HAVE_TEUCHOS_COMPLEX
868 # define UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(TEST_GROUP, TEST_NAME, ORDINAL)\
869  typedef std::complex<float> ComplexFloat; \
870  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT(TEST_GROUP, TEST_NAME, ORDINAL, ComplexFloat)
871 # define UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(TEST_GROUP, TEST_NAME, ORDINAL)\
872  typedef std::complex<double> ComplexDouble; \
873  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT(TEST_GROUP, TEST_NAME, ORDINAL, ComplexDouble)
874 #else
875 # define UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(TEST_GROUP, TEST_NAME, ORDINAL)
876 # define UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(TEST_GROUP, TEST_NAME, ORDINAL)
877 #endif
878 
879 
880 #define UNIT_TEST_GROUP_ORDINAL_PACKET( ORDINAL, PACKET ) \
881  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, NonblockingSendReceive, ORDINAL, PACKET ) \
882  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, NonblockingSendReceive_isReady_true, ORDINAL, PACKET ) \
883  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, NonblockingSendReceive_isReady_false, ORDINAL, PACKET ) \
884  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, NonblockingSendReceive_isReady_nullIsTrue, ORDINAL, PACKET ) \
885  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, NonblockingSendReceiveSet, ORDINAL, PACKET ) \
886  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, ReadySend1, ORDINAL, PACKET ) \
887  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, ReadySend, ORDINAL, PACKET )
888 
889 #ifdef HAVE_TEUCHOS_QD
890 # define UNIT_TEST_GROUP_ORDINAL_QD(ORDINAL) \
891  UNIT_TEST_GROUP_ORDINAL_PACKET(ORDINAL, dd_real) \
892  UNIT_TEST_GROUP_ORDINAL_PACKET(ORDINAL, qd_real)
893 #else
894 # define UNIT_TEST_GROUP_ORDINAL_QD(ORDINAL)
895 #endif
896 
897 #define UNIT_TEST_GROUP_ORDINAL_PAIROFPACKETS( ORDINAL, PAIROFPACKETS ) \
898  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, NonblockingSendReceive, ORDINAL, PAIROFPACKETS ) \
899  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, NonblockingSendReceive_isReady_true, ORDINAL, PAIROFPACKETS ) \
900  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, NonblockingSendReceive_isReady_false, ORDINAL, PAIROFPACKETS ) \
901  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, NonblockingSendReceive_isReady_nullIsTrue, ORDINAL, PAIROFPACKETS ) \
902  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, NonblockingSendReceiveSet, ORDINAL, PAIROFPACKETS ) \
903  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, ReadySend1, ORDINAL, PAIROFPACKETS ) \
904  TEUCHOS_UNIT_TEST_TEMPLATE_2_INSTANT( DefaultMpiComm, ReadySend, ORDINAL, PAIROFPACKETS )
905 
906 #define UNIT_TEST_GROUP_ORDINAL_SUBCOMMUNICATORS( ORDINAL ) \
907  TEUCHOS_UNIT_TEST_TEMPLATE_1_INSTANT( DefaultMpiComm, duplicate, ORDINAL ) \
908  TEUCHOS_UNIT_TEST_TEMPLATE_1_INSTANT( DefaultMpiComm, split, ORDINAL ) \
909  TEUCHOS_UNIT_TEST_TEMPLATE_1_INSTANT( DefaultMpiComm, createSubcommunicator, ORDINAL )
910 
911 
912 typedef std::pair<short, short> PairOfShorts;
913 typedef std::pair<int,int> PairOfInts;
914 typedef std::pair<float,float> PairOfFloats;
915 typedef std::pair<double,double> PairOfDoubles;
916 
917 
918 // Uncomment this for really fast development cycles but make sure to comment
919 // it back again before checking in so that we can test all the types.
920 // #define FAST_DEVELOPMENT_UNIT_TEST_BUILD
921 
922 
923 #ifdef FAST_DEVELOPMENT_UNIT_TEST_BUILD
924 
925 # define UNIT_TEST_GROUP_ORDINAL( ORDINAL ) \
926  UNIT_TEST_GROUP_ORDINAL_PACKET(ORDINAL, double) \
927  UNIT_TEST_GROUP_ORDINAL_PAIROFPACKETS(ORDINAL, PairOfDoubles) \
928 
930 
931 #else // FAST_DEVELOPMENT_UNIT_TEST_BUILD
932 
933 # define UNIT_TEST_GROUP_ORDINAL( ORDINAL ) \
934  TEUCHOS_UNIT_TEST_TEMPLATE_1_INSTANT( DefaultMpiComm, basic, ORDINAL ) \
935  UNIT_TEST_GROUP_ORDINAL_PACKET(ORDINAL, short) \
936  UNIT_TEST_GROUP_ORDINAL_PACKET(ORDINAL, int) \
937  UNIT_TEST_GROUP_ORDINAL_PACKET(ORDINAL, float) \
938  UNIT_TEST_GROUP_ORDINAL_PACKET(ORDINAL, double) \
939  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, NonblockingSendReceive, ORDINAL) \
940  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, NonblockingSendReceive_isReady_true, ORDINAL) \
941  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, NonblockingSendReceive_isReady_false, ORDINAL) \
942  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, NonblockingSendReceive_isReady_nullIsTrue, ORDINAL) \
943  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, ReadySend1, ORDINAL) \
944  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, ReadySend, ORDINAL) \
945  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, NonblockingSendReceive, ORDINAL) \
946  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, NonblockingSendReceive_isReady_true, ORDINAL) \
947  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, NonblockingSendReceive_isReady_false, ORDINAL) \
948  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, NonblockingSendReceive_isReady_nullIsTrue, ORDINAL) \
949  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, ReadySend1, ORDINAL) \
950  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, ReadySend, ORDINAL) \
951  UNIT_TEST_GROUP_ORDINAL_SUBCOMMUNICATORS(ORDINAL)
952 
953 # define UNIT_TEST_GROUP_ORDINAL_WITH_PAIRS_AND_QD( ORDINAL ) \
954  TEUCHOS_UNIT_TEST_TEMPLATE_1_INSTANT( DefaultMpiComm, basic, ORDINAL ) \
955  UNIT_TEST_GROUP_ORDINAL_PACKET(ORDINAL, short) \
956  UNIT_TEST_GROUP_ORDINAL_PACKET(ORDINAL, int) \
957  UNIT_TEST_GROUP_ORDINAL_PACKET(ORDINAL, float) \
958  UNIT_TEST_GROUP_ORDINAL_PACKET(ORDINAL, double) \
959  UNIT_TEST_GROUP_ORDINAL_QD(ORDINAL) \
960  UNIT_TEST_GROUP_ORDINAL_PAIROFPACKETS(ORDINAL, PairOfShorts) \
961  UNIT_TEST_GROUP_ORDINAL_PAIROFPACKETS(ORDINAL, PairOfInts) \
962  UNIT_TEST_GROUP_ORDINAL_PAIROFPACKETS(ORDINAL, PairOfFloats) \
963  UNIT_TEST_GROUP_ORDINAL_PAIROFPACKETS(ORDINAL, PairOfDoubles) \
964  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, NonblockingSendReceive, ORDINAL) \
965  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, NonblockingSendReceive_isReady_true, ORDINAL) \
966  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, NonblockingSendReceive_isReady_false, ORDINAL) \
967  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, NonblockingSendReceive_isReady_nullIsTrue, ORDINAL) \
968  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, ReadySend1, ORDINAL) \
969  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_FLOAT(DefaultMpiComm, ReadySend, ORDINAL) \
970  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, NonblockingSendReceive, ORDINAL) \
971  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, NonblockingSendReceive_isReady_true, ORDINAL) \
972  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, NonblockingSendReceive_isReady_false, ORDINAL) \
973  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, NonblockingSendReceive_isReady_nullIsTrue, ORDINAL) \
974  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, ReadySend1, ORDINAL) \
975  UNIT_TEST_TEMPLATE_2_INSTANT_COMPLEX_DOUBLE(DefaultMpiComm, ReadySend, ORDINAL)
976 
977  typedef short int ShortInt;
978  UNIT_TEST_GROUP_ORDINAL(ShortInt)
980  typedef long int LongInt;
981  UNIT_TEST_GROUP_ORDINAL(LongInt) // can't do QD with LongInt, one of the tests complains
982 
983  typedef long long int LongLongInt;
984  UNIT_TEST_GROUP_ORDINAL(LongLongInt)
985 
986 #endif // FAST_DEVELOPMENT_UNIT_TEST_BUILD
987 
988 
989 } // namespace
RCP< T > rcp(const boost::shared_ptr< T > &sptr)
Conversion function that takes in a boost::shared_ptr object and spits out a Teuchos::RCP object...
static std::pair< Packet, Packet > real(std::pair< Packet, Packet > x)
#define TEST_ASSERT(v1)
Assert the given statement is true.
void addOutputSetupOptions(const bool &addOutputSetupOptions)
Set if options will be automatically added to setup Teuchos::VerboseObjectBase::getDefaultOStream().
#define UNIT_TEST_GROUP_ORDINAL_WITH_PAIRS_AND_QD(ORDINAL)
Scalar defaultSmallNumber()
void broadcast(const Comm< Ordinal > &comm, const int rootRank, const Ordinal count, Packet buffer[])
Broadcast array of objects that use value semantics.
#define ECHO(statement)
Echo the given statement before it is executed.
RCP< T2 > rcp_dynamic_cast(const RCP< T1 > &p1, bool throw_on_fail=false)
Dynamic cast of underlying RCP type from T1* to T2*.
static bool isnaninf(std::pair< Packet, Packet > x)
static CommandLineProcessor & getCLP()
Return the CLP to add options to.
static magnitudeType magnitude(std::pair< Packet, Packet > a)
bool is_null(const std::shared_ptr< T > &p)
Returns true if p.get()==NULL.
static const bool isComparable
Determines if scalar type supports relational operators such as &lt;, &gt;, &lt;=, &gt;=.
#define TEUCHOS_UNIT_TEST_TEMPLATE_1_DECL(TEST_GROUP, TEST_NAME, TYPE)
Macro for defining a templated unit test with one template parameter.
int rank(const Comm< Ordinal > &comm)
Get the process rank.
#define TEST_EQUALITY(v1, v2)
Assert the equality of v1 and v2.
#define TEUCHOS_UNIT_TEST_TEMPLATE_2_DECL(TEST_GROUP, TEST_NAME, TYPE1, TYPE2)
Macro for defining a templated unit test with two template parameters.
Concrete serial communicator subclass.
#define TEUCHOS_UNIT_TEST(TEST_GROUP, TEST_NAME)
Macro for defining a (non-templated) unit test.
static std::pair< Packet, Packet > squareroot(std::pair< Packet, Packet > x)
static Teuchos::RCP< const Comm< OrdinalType > > getComm()
Return the default global communicator.
Initialize, finalize, and query the global MPI session.
static const bool hasMachineParameters
Determines if scalar type have machine-specific parameters (i.e. eps(), sfmin(), base(), prec(), t(), rnd(), emin(), rmin(), emax(), rmax() are supported).
bool is_null(const ArrayRCP< T > &p)
Returns true if p.get()==NULL.
static std::pair< Packet, Packet > imag(std::pair< Packet, Packet > x)
void reduceAll(const Comm< Ordinal > &comm, const ValueTypeReductionOp< Ordinal, Packet > &reductOp, const Ordinal count, const Packet sendBuffer[], Packet globalReducts[])
Wrapper for MPI_Allreduce that takes a custom reduction operator.
static std::pair< Packet, Packet > pow(std::pair< Packet, Packet > x, std::pair< Packet, Packet > y)
This structure defines some basic traits for a scalar field type.
std::vector< std::string > split(const std::string &str, const std::string &delimiters, const size_t start)
Split the given string using the given set of delimiters.
TEUCHOS_DEPRECATED RCP< T > rcp(T *p, Dealloc_T dealloc, bool owns_mem)
Deprecated.
void setOption(const char option_true[], const char option_false[], bool *option_val, const char documentation[]=NULL)
Set a boolean option.
void waitAll(const Comm< Ordinal > &comm, const ArrayView< RCP< CommRequest< Ordinal > > > &requests)
Wait for an array of Teuchos::CommRequest objects.
#define UNIT_TEST_GROUP_ORDINAL(ORDINAL)
Unit testing support.
Implementation of Teuchos wrappers for MPI.
#define TEST_EQUALITY_CONST(v1, v2)
Assert the equality of v1 and constant v2.
void barrier(const Comm< Ordinal > &comm)
Barrier.
Ptr< T > inoutArg(T &arg)
create a non-persisting (required or optional) input/output argument for a function call...
Return a default global communicator appropriate for the build.
int size(const Comm< Ordinal > &comm)
Get the number of processes in the communicator.
Default traits class for all conversions between value types.
Definition: Teuchos_as.hpp:147
TypeTo as(const TypeFrom &t)
Convert from one value type to another.
RCP< CommRequest< Ordinal > > ireceive(const ArrayRCP< Packet > &recvBuffer, const int sourceRank, const int tag, const Comm< Ordinal > &comm)
Variant of ireceive that takes a tag argument (and restores the correct order of arguments).
Abstract interface for distributed-memory communication.
#define TEST_COMPARE_ARRAYS(a1, a2)
Assert that a1.size()==a2.size() and a[i]==b[i], i=0....
std::pair< typename PST::magnitudeType, typename PST::magnitudeType > magnitudeType
RCP< Teuchos::CommRequest< int > > isend(const ArrayRCP< const double > &sendBuffer, const int destRank, const int tag, const Comm< int > &comm)
RCP< T > rcpFromRef(T &r)
Return a non-owning weak RCP object from a raw object reference for a defined type.
RCP< CommStatus< Ordinal > > wait(const Comm< Ordinal > &comm, const Ptr< RCP< CommRequest< Ordinal > > > &request)
Wait on a single communication request, and return its status.
Smart reference counting pointer class for automatic garbage collection.
static std::pair< Packet, Packet > conjugate(std::pair< Packet, Packet > x)
static const bool isComplex
Determines if scalar type is std::complex.
Ptr< T > outArg(T &arg)
create a non-persisting (required or optional) output argument for a function call.
Definition of Teuchos::as, for conversions between types.
void readySend(const Packet sendBuffer[], const Ordinal count, const int destRank, const int tag, const Comm< Ordinal > &comm)
Variant of readySend() that accepts a message tag.
Class that helps parse command line input arguments from (argc,argv[]) and set options.
TEUCHOS_STATIC_SETUP()
Reference-counted smart pointer for managing arrays.
Replacement for std::vector that is compatible with the Teuchos Memory Management classes...