KaMPIng 0.2.1
(Near) zero-overhead MPI wrapper for C++
Loading...
Searching...
No Matches
mpi_type_traits.hpp
Go to the documentation of this file.
1// This file is part of KaMPIng.
2//
3// Copyright 2021-2026 The KaMPIng Authors
4//
5// KaMPIng is free software : you can redistribute it and/or modify it under the terms of the GNU Lesser General Public
6// License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later
7// version. KaMPIng is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the
8// implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
9// for more details.
10//
11// You should have received a copy of the GNU Lesser General Public License along with KaMPIng. If not, see
12// <https://www.gnu.org/licenses/>.
13
14/// @file
15/// @brief Type traits and dispatcher for mapping C++ types to MPI datatypes.
16
17#pragma once
18#include <type_traits>
19
23
24namespace kamping::types {
25
26/// @addtogroup kamping_types
27/// @{
28
29/// @brief Maps a C++ type \p T to a type trait for constructing an MPI_Datatype.
30///
31/// | C++ type | Result |
32/// |----------|--------|
33/// | MPI builtin (`int`, `double`, …, `kabool`) | `builtin_type<T>` |
34/// | Enum | dispatches to `type_dispatcher<underlying_type>()` |
35/// | `T[N]`, `std::array<T, N>` | `contiguous_type<T, N>` |
36/// | Everything else | `internal::no_matching_type` |
37///
38/// Specialize \ref kamping::types::mpi_type_traits to handle additional types.
39///
40/// @returns The corresponding type trait for the type \p T.
41template <typename T>
43 using T_no_const = std::remove_const_t<T>;
44
45 static_assert(
46 !std::is_pointer_v<T_no_const>,
47 "MPI does not support pointer types. Why do you want to transfer a pointer over MPI?"
48 );
49 static_assert(!std::is_function_v<T_no_const>, "MPI does not support function types.");
50 static_assert(!std::is_union_v<T_no_const>, "MPI does not support union types.");
51 static_assert(!std::is_void_v<T_no_const>, "There is no MPI datatype corresponding to void.");
52
53 if constexpr (is_builtin_type_v<T_no_const>) {
55 } else if constexpr (std::is_enum_v<T_no_const>) {
57 } else if constexpr (std::is_array_v<T_no_const>) {
58 return contiguous_type<std::remove_extent_t<T_no_const>, std::extent_v<T_no_const>>{};
60 return contiguous_type<
63 } else {
65 }
66}
67
68/// @brief Whether the type is handled by the auto-dispatcher \ref kamping::types::type_dispatcher().
69template <typename T>
70static constexpr bool has_auto_dispatched_type_v =
71 !std::is_same_v<decltype(type_dispatcher<T>()), kamping::internal::no_matching_type>;
72
73/// @brief The type trait that maps a C++ type \p T to an MPI_Datatype for the kamping-types module.
74///
75/// The default behavior is controlled by \ref kamping::types::type_dispatcher(). Specialize this
76/// trait to support additional types within the module.
77/// Upper-level frameworks (e.g., full KaMPIng) define their own extension point on top.
78template <typename T, typename Enable = void>
80
81/// @brief Partial specialization of \ref kamping::types::mpi_type_traits for types matched by
82/// \ref kamping::types::type_dispatcher().
83template <typename T>
84struct mpi_type_traits<T, std::enable_if_t<has_auto_dispatched_type_v<T>>> {
85 /// @brief The base type of this trait obtained via \ref kamping::types::type_dispatcher().
86 using base = decltype(type_dispatcher<T>());
87 /// @brief The category of the type.
88 static constexpr TypeCategory category = base::category;
89 /// @brief Whether the type has to be committed before it can be used in MPI calls.
90 static constexpr bool has_to_be_committed = category_has_to_be_committed(category);
91 /// @brief The MPI_Datatype corresponding to the type T.
93 return decltype(type_dispatcher<T>())::data_type();
94 }
95};
96
97/// @brief Check if the type has a static type definition, i.e. \ref kamping::types::mpi_type_traits is defined.
98template <typename, typename Enable = void>
99struct has_static_type : std::false_type {};
100
101/// @brief Check if the type has a static type definition, i.e. \ref kamping::types::mpi_type_traits is defined.
102template <typename T>
103struct has_static_type<T, std::void_t<decltype(mpi_type_traits<T>::data_type())>> : std::true_type {};
104
105/// @brief `true` if \ref kamping::types::mpi_type_traits provides a `data_type()` function.
106template <typename T>
108
109/// @brief Default lookup policy for \ref contiguous_type and \ref struct_type.
110///
111/// Resolves the MPI_Datatype for a type \p T by consulting \ref kamping::types::mpi_type_traits.
112/// Users of the kamping-types module can extend the supported types by specializing
113/// \ref kamping::types::mpi_type_traits. Upper-level frameworks may supply an alternative Lookup
114/// policy (e.g., to add a byte-serialization fallback).
116 /// @brief `true` if the Lookup can resolve an MPI_Datatype for \p T.
117 template <typename T>
118 static constexpr bool has_type_v = has_static_type_v<T>;
119
120 /// @brief Returns the MPI_Datatype for \p T.
121 template <typename T>
122 static MPI_Datatype get() {
124 }
125};
126
127/// @}
128
129} // namespace kamping::types
STL-compatible allocator for requesting memory using the builtin MPI allocator.
Definition allocator.hpp:32
Forward declarations for contiguous_type and byte_serialized to break include cycles.
TypeCategory
Type groups as defined in Section 6.9.2 of the MPI 4.0 standard.
Definition builtin_types.hpp:32
auto type_dispatcher()
Maps a C++ type T to a type trait for constructing an MPI_Datatype.
Definition mpi_type_traits.hpp:42
static constexpr bool has_auto_dispatched_type_v
Whether the type is handled by the auto-dispatcher kamping::types::type_dispatcher().
Definition mpi_type_traits.hpp:70
static constexpr bool has_static_type_v
true if kamping::types::mpi_type_traits provides a data_type() function.
Definition mpi_type_traits.hpp:107
constexpr bool category_has_to_be_committed(TypeCategory category)
Returns whether an MPI_Datatype of the given category must be committed before use.
Definition builtin_types.hpp:35
Mapping of C++ datatypes to builtin MPI types.
STL namespace.
Helper to check if a type is a std::array.
Definition type_helpers.hpp:42
Type tag for indicating that no static type definition exists for a type.
Definition type_helpers.hpp:52
Constructs a contiguous MPI type of N elements of type T using MPI_Type_contiguous.
Definition contiguous_type_fwd.hpp:39
Check if the type has a static type definition, i.e. kamping::types::mpi_type_traits is defined.
Definition mpi_type_traits.hpp:99
static MPI_Datatype data_type()
The MPI_Datatype corresponding to the type T.
Definition mpi_type_traits.hpp:92
The type trait that maps a C++ type T to an MPI_Datatype for the kamping-types module.
Definition mpi_type_traits.hpp:79
Default lookup policy for contiguous_type and struct_type.
Definition mpi_type_traits.hpp:115
static constexpr bool has_type_v
true if the Lookup can resolve an MPI_Datatype for T.
Definition mpi_type_traits.hpp:118
static MPI_Datatype get()
Returns the MPI_Datatype for T.
Definition mpi_type_traits.hpp:122
Internal type helpers for the kamping-types module.