1 #pragma once 2 #include <sdbusplus/utility/dedup_variant.hpp> 3 4 #include <variant> 5 6 /** See `sdbusplus::utility::merge_variants` below. */ 7 8 namespace sdbusplus 9 { 10 namespace utility 11 { 12 13 namespace details 14 { 15 16 /** Find the deduplicated variant type. 17 * 18 * @tparam T - A type of the form 'variant<...>'. 19 * @tparam Unused - An empty type set (non-empty sets are matched in 20 * specialization). 21 * 22 * This template is only matched when Unused is empty, which means all 23 * types have been processed (merged). 24 */ 25 template <typename T, typename... Unused> 26 struct merge_variants 27 { 28 using type = T; 29 static_assert(sizeof...(Unused) == 0); 30 }; 31 32 /** Compute the merged variant type. 33 * 34 * @tparam D - Done - Head and tail of the alternative types list of the 35 * first variant. 36 * @tparam Next - The types of the next variant<...> to be merged with the 37 * first. 38 * @tparam Rest - The remaining variants to be merged. 39 * 40 * Use dedup_variant_t to recursively combine alternative types of all the 41 * supplied variants without duplication. 42 */ 43 template <typename D, typename... Done, typename... Next, typename... Rest> 44 struct merge_variants<std::variant<D, Done...>, std::variant<Next...>, 45 Rest...> : 46 public merge_variants< 47 sdbusplus::utility::dedup_variant_t<D, Done..., Next...>, Rest...> 48 {}; 49 50 } // namespace details 51 52 /** This type is useful for processing D-Bus messages containing information for 53 * multiple interfaces. For doing sdbusplus::message::message::read() on them 54 * one needs to define an std::variant which would be a combination of all the 55 * PropertiesVariant's involved. */ 56 template <typename... T> 57 using merge_variants_t = typename details::merge_variants<T...>::type; 58 59 } // namespace utility 60 } // namespace sdbusplus 61