1 #ifndef MPQC_MPI_BASE_HPP
2 #define MPQC_MPI_BASE_HPP
4 #include "mpqc_config.h"
7 #define OMPI_SKIP_MPICXX
8 #define MPICH_SKIP_MPICXX
12 #include "mpqc/utility/mutex.hpp"
16 #include <boost/thread.hpp>
24 void initialize(
int thread_level);
26 std::string get_processor_name();
31 inline void initialize(
int thread_level) {}
32 inline void finalize() {}
33 inline std::string get_processor_name() {
return "localhost"; }
40 struct threadsafe : boost::noncopyable {
45 int thread = MPI_THREAD_SINGLE;
46 MPI_Query_thread(&thread);
47 if (thread != MPI_THREAD_MULTIPLE) {
48 mutex::global::lock();
53 if (locked_) mutex::global::unlock();
58 #define MPQC_MPI_THREADSAFE threadsafe _threadsafe;
67 #define MPQC_MPI_TYPE(T, MPI_DATATYPE) \
68 template<> inline MPI_Datatype type<T>() { return MPI_DATATYPE; }
70 MPQC_MPI_TYPE(
int, MPI_INT)
71 MPQC_MPI_TYPE(
double, MPI_DOUBLE)
75 inline void initialize(
int thread_level) {
77 MPI_Initialized(&initialized);
82 MPI_Init_thread(&argc, &argv, MPI_THREAD_MULTIPLE, &thread);
84 int thread = MPI_THREAD_SINGLE;
85 MPI_Query_thread(&thread);
86 if (thread < MPI_THREAD_SERIALIZED) {
87 throw std::runtime_error(
"thread < MPI_THREAD_SERIALIZED");
91 inline void finalize() {
95 inline std::string get_processor_name() {
96 char name[MPI_MAX_PROCESSOR_NAME];
98 MPI_Get_processor_name(name, &len);
99 return std::string(name, len);
102 inline MPI_Status wait(MPI_Request request,
size_t us = 0) {
103 MPQC_MPI_THREADSAFE {
106 MPI_Wait(&request, &status);
111 MPI_Test(&request, &flag, &status);
112 if (flag)
return status;
113 boost::this_thread::sleep(boost::posix_time::microseconds(us));
125 #endif // MPQC_MPI_BASE_HPP