20 virtual ~OpLog() { req_free(); }
22 auto operator<=>(
const OpLog& o)
const {
return m_idx <=> o.m_idx; }
23 auto operator<=>(
const int& i)
const {
return m_idx <=> i; }
24 auto operator==(
const OpLog& o)
const {
return m_idx == o.m_idx; }
25 auto operator==(
const int& i)
const {
return m_idx == i; }
27 void serialize(std::ostream& o)
const {
28 serialize::write(o, m_idx);
29 this->serialize_impl(o);
32 MPI_Request* req()
const {
return m_req; }
33 int idx()
const {
return m_idx; }
38 virtual void serialize_impl(std::ostream& o)
const = 0;
39 virtual std::string str()
const = 0;
42 OpLog() : m_idx(-1) {}
43 OpLog(
int i) : m_idx(i) {}
44 OpLog(std::istream& i) :
OpLog(serialize::read<int>(i)) {}
51 void req_set(MPI_Request* new_ptr)
const {
55 void req_free()
const {
56 if (req_obj != MPI_REQUEST_NULL) {
57 if (!util::mpi_finalized()) MPI_Request_free(&req_obj);
58 req_obj = MPI_REQUEST_NULL;
66 mutable MPI_Request req_obj = MPI_REQUEST_NULL;
67 mutable MPI_Request* m_req = &req_obj;
105 o.m_type = MPI_DATATYPE_NULL;
106 internal_buf = std::move(o.internal_buf);
107 user_buf = o.user_buf;
108 o.user_buf =
nullptr;
113 static MPIBuffer wrap(
void* user_buffer,
int count, MPI_Datatype type) {
114 return MPIBuffer(user_buffer, count, type);
117 static MPIBuffer create(
int count, MPI_Datatype type) {
121 static MPIBuffer copy(
const void* user_buffer,
int count, MPI_Datatype type) {
122 return MPIBuffer(count, type,
static_cast<const char*
>(user_buffer));
126 operator bool()
const {
return m_type != MPI_DATATYPE_NULL; }
128 void copy_to(
void* out) {
129 std::memcpy(out, buf(), m_count * util::type_size(m_type));
131 void copy_from(
void* in) {
132 std::memcpy(buf(), in, m_count * util::type_size(m_type));
136 void release_user_buf()
const { user_buf =
nullptr; }
138 void serialize(std::ostream& o)
const {
139 serialize::write(o, m_type);
140 serialize::write(o, m_count);
142 int size = garbage_data ? 0 : internal_buf.size();
143 serialize::write<int>(o, size);
144 if (size > 0) serialize::write(o, internal_buf.data(), size);
147 serialize::read(i, m_type);
148 serialize::read(i, m_count);
150 int size = serialize::read<int>(i);
152 internal_buf.resize(size);
153 serialize::read(i, &internal_buf[0], size);
160 fenix_assert(internal_buf.empty());
163 if (internal_buf.empty()) {
167 internal_buf.resize(m_count * util::type_size(m_type));
169 fenix_assert(internal_buf.size() == m_count * util::type_size(m_type));
170 return internal_buf.data();
172 int count()
const {
return m_count; }
173 MPI_Datatype type()
const {
return m_type; }
175 operator void*()
const {
return buf(); }
176 operator int()
const {
return m_count; }
177 operator MPI_Datatype()
const {
return m_type; }
181 MPIBuffer(
void* user_buffer,
int count, MPI_Datatype type)
182 : user_buf(user_buffer), m_count(count), m_type(type) {};
184 MPIBuffer(
int count, MPI_Datatype type,
const char* b)
185 : internal_buf(b, b + count * util::type_size(type)), m_count(count),
188 MPIBuffer(
int count, MPI_Datatype type) : m_count(count), m_type(type) {};
190 mutable void* user_buf =
nullptr;
191 mutable std::vector<char> internal_buf;
194 mutable bool garbage_data =
false;
197 MPI_Datatype m_type = MPI_DATATYPE_NULL;