27#ifndef SDBUS_CXX_TYPETRAITS_H_
28#define SDBUS_CXX_TYPETRAITS_H_
39# if __has_include(<span>)
47#include <unordered_map>
55 template <
typename... _ValueTypes>
class Struct;
59 template<
typename _T1,
typename _T2>
using DictEntry = std::pair<_T1, _T2>;
67 class PropertySetCall;
68 class PropertyGetReply;
69 template <
typename... _Results>
class Result;
71 template <
typename _T,
typename _Enable =
void>
struct signature_of;
77 using method_callback = std::function<void(MethodCall msg)>;
78 using async_reply_handler = std::function<void(MethodReply reply, std::optional<Error> error)>;
79 using signal_handler = std::function<void(Signal signal)>;
80 using message_handler = std::function<void(Message msg)>;
81 using property_set_callback = std::function<void(PropertySetCall msg)>;
82 using property_get_callback = std::function<void(PropertyGetReply& reply)>;
85 using Slot = std::unique_ptr<void, std::function<void(
void*)>>;
114 template <
class... _T>
constexpr bool always_false =
false;
117 template <
typename _T, std::
size_t _N1, std::
size_t _N2>
118 constexpr std::array<_T, _N1 + _N2> operator+(std::array<_T, _N1> lhs, std::array<_T, _N2> rhs);
121 template <
typename _T>
122 constexpr auto signature_of_v = signature_of<_T>::value;
124 template <
typename _T,
typename _Enable>
127 static constexpr bool is_valid =
false;
128 static constexpr bool is_trivial_dbus_type =
false;
130 static constexpr void* value = []
134 static_assert(always_false<_T>,
"Unsupported D-Bus type (specialize `signature_of` for your custom types)");
138 template <
typename _T>
142 template <
typename _T>
146 template <
typename _T>
150 template <
typename _T>
157 static constexpr std::array<char, 0> value{};
158 static constexpr bool is_valid =
true;
159 static constexpr bool is_trivial_dbus_type =
false;
165 static constexpr std::array value{
'b'};
166 static constexpr bool is_valid =
true;
167 static constexpr bool is_trivial_dbus_type =
true;
173 static constexpr std::array value{
'y'};
174 static constexpr bool is_valid =
true;
175 static constexpr bool is_trivial_dbus_type =
true;
181 static constexpr std::array value{
'n'};
182 static constexpr bool is_valid =
true;
183 static constexpr bool is_trivial_dbus_type =
true;
189 static constexpr std::array value{
'q'};
190 static constexpr bool is_valid =
true;
191 static constexpr bool is_trivial_dbus_type =
true;
197 static constexpr std::array value{
'i'};
198 static constexpr bool is_valid =
true;
199 static constexpr bool is_trivial_dbus_type =
true;
205 static constexpr std::array value{
'u'};
206 static constexpr bool is_valid =
true;
207 static constexpr bool is_trivial_dbus_type =
true;
213 static constexpr std::array value{
'x'};
214 static constexpr bool is_valid =
true;
215 static constexpr bool is_trivial_dbus_type =
true;
221 static constexpr std::array value{
't'};
222 static constexpr bool is_valid =
true;
223 static constexpr bool is_trivial_dbus_type =
true;
229 static constexpr std::array value{
'd'};
230 static constexpr bool is_valid =
true;
231 static constexpr bool is_trivial_dbus_type =
true;
237 static constexpr std::array value{
's'};
238 static constexpr bool is_valid =
true;
239 static constexpr bool is_trivial_dbus_type =
false;
254 template <std::
size_t _N>
258 template <std::
size_t _N>
274 template <
typename... _ValueTypes>
277 static constexpr std::array contents = (signature_of_v<_ValueTypes> + ...);
278 static constexpr std::array value = std::array{
'('} + contents + std::array{
')'};
279 static constexpr char type_value{
'r'};
280 static constexpr bool is_valid =
true;
281 static constexpr bool is_trivial_dbus_type =
false;
287 static constexpr std::array value{
'v'};
288 static constexpr bool is_valid =
true;
289 static constexpr bool is_trivial_dbus_type =
false;
292 template <
typename... Elements>
299 static constexpr std::array value{
'o'};
300 static constexpr bool is_valid =
true;
301 static constexpr bool is_trivial_dbus_type =
false;
307 static constexpr std::array value{
'g'};
308 static constexpr bool is_valid =
true;
309 static constexpr bool is_trivial_dbus_type =
false;
315 static constexpr std::array value{
'h'};
316 static constexpr bool is_valid =
true;
317 static constexpr bool is_trivial_dbus_type =
false;
320 template <
typename _T1,
typename _T2>
323 static constexpr std::array value = std::array{
'{'} + signature_of_v<std::tuple<_T1, _T2>> + std::array{
'}'};
324 static constexpr char type_value{
'e'};
325 static constexpr bool is_valid =
true;
326 static constexpr bool is_trivial_dbus_type =
false;
329 template <
typename _Element,
typename _Allocator>
332 static constexpr std::array value = std::array{
'a'} + signature_of_v<_Element>;
333 static constexpr bool is_valid =
true;
334 static constexpr bool is_trivial_dbus_type =
false;
337 template <
typename _Element, std::
size_t _Size>
343 template <
typename _Element, std::
size_t _Extent>
349 template <
typename _Enum>
350 struct signature_of<_Enum, typename std::enable_if_t<std::is_enum_v<_Enum> && !std::is_const_v<_Enum> && !std::is_volatile_v<_Enum>>>
354 template <
typename _Key,
typename _Value,
typename _Compare,
typename _Allocator>
357 static constexpr std::array value = std::array{
'a'} + signature_of_v<DictEntry<_Key, _Value>>;
358 static constexpr bool is_valid =
true;
359 static constexpr bool is_trivial_dbus_type =
false;
362 template <
typename _Key,
typename _Value,
typename _Hash,
typename _KeyEqual,
typename _Allocator>
363 struct signature_of<std::unordered_map<_Key, _Value, _Hash, _KeyEqual, _Allocator>>
368 template <
typename... _Types>
371 static constexpr std::array value = (std::array<char, 0>{} + ... + signature_of_v<_Types>);
372 static constexpr bool is_valid =
false;
373 static constexpr bool is_trivial_dbus_type =
false;
377 template <
typename _T, std::
size_t _N>
378 constexpr auto as_null_terminated(std::array<_T, _N> arr)
380 return arr + std::array<_T, 1>{0};
385 template <
typename _Type>
389 template <
typename _Type>
393 template <
typename _Type>
397 template <
typename _ReturnType,
typename... _Args>
400 typedef _ReturnType result_type;
401 typedef std::tuple<_Args...> arguments_type;
402 typedef std::tuple<std::decay_t<_Args>...> decayed_arguments_type;
404 typedef _ReturnType function_type(_Args...);
406 static constexpr std::size_t arity =
sizeof...(_Args);
423 template <
size_t _Idx>
426 typedef std::tuple_element_t<_Idx, std::tuple<_Args...>> type;
429 template <
size_t _Idx>
430 using arg_t =
typename arg<_Idx>::type;
433 template <
typename _ReturnType,
typename... _Args>
436 static constexpr bool is_async =
false;
437 static constexpr bool has_error_param =
false;
440 template <
typename... _Args>
443 static constexpr bool has_error_param =
true;
446 template <
typename... _Args,
typename... _Results>
449 static constexpr bool is_async =
true;
450 using async_result_t =
Result<_Results...>;
453 template <
typename... _Args,
typename... _Results>
456 static constexpr bool is_async =
true;
457 using async_result_t =
Result<_Results...>;
460 template <
typename _ReturnType,
typename... _Args>
464 template <
typename _ClassType,
typename _ReturnType,
typename... _Args>
467 typedef _ClassType& owner_type;
470 template <
typename _ClassType,
typename _ReturnType,
typename... _Args>
473 typedef const _ClassType& owner_type;
476 template <
typename _ClassType,
typename _ReturnType,
typename... _Args>
479 typedef volatile _ClassType& owner_type;
482 template <
typename _ClassType,
typename _ReturnType,
typename... _Args>
485 typedef const volatile _ClassType& owner_type;
488 template <
typename FunctionType>
492 template <
class _Function>
495 template <
class _Function>
498 template <
typename _FunctionType>
501 template <
typename _FunctionType,
size_t _Idx>
504 template <
typename _FunctionType>
507 template <
typename _FunctionType>
510 template <
typename _Function>
516 template <
typename _Function>
517 using tuple_of_function_input_arg_types_t =
typename tuple_of_function_input_arg_types<_Function>::type;
519 template <
typename _Function>
525 template <
typename _Function>
526 using tuple_of_function_output_arg_types_t =
typename tuple_of_function_output_arg_types<_Function>::type;
528 template <
typename _Function>
531 static std::string value_as_string()
533 constexpr auto signature = as_null_terminated(signature_of_v<tuple_of_function_input_arg_types_t<_Function>>);
534 return signature.data();
538 template <
typename _Function>
541 template <
typename _Function>
544 static std::string value_as_string()
546 constexpr auto signature = as_null_terminated(signature_of_v<tuple_of_function_output_arg_types_t<_Function>>);
547 return signature.data();
551 template <
typename _Function>
557 typedef std::tuple<_Args...> type;
570 template <
typename... _Args>
571 using future_return_t =
typename future_return<_Args...>::type;
574 template <
typename,
typename>
575 constexpr bool is_one_of_variants_types =
false;
577 template <
typename... _VariantTypes,
typename _QueriedType>
578 constexpr bool is_one_of_variants_types<std::variant<_VariantTypes...>, _QueriedType>
579 = (std::is_same_v<_QueriedType, _VariantTypes> || ...);
583 template <
typename _Struct>
587 const _Struct& m_struct;
590 template <
typename _Type>
591 const _Type& as_dictionary_if_struct(
const _Type&
object)
600 template <
typename _Struct>
601 constexpr auto strict_dict_as_struct_deserialization_v =
true;
608 template <
typename _Struct>
609 constexpr auto nested_struct_as_dict_serialization_v =
false;
613 template <
class _Function,
class _Tuple,
typename... _Args, std::size_t... _I>
614 constexpr decltype(
auto) apply_impl( _Function&& f
615 , Result<_Args...>&& r
617 , std::index_sequence<_I...> )
619 return std::forward<_Function>(f)(std::move(r), std::get<_I>(std::forward<_Tuple>(t))...);
622 template <
class _Function,
class _Tuple, std::size_t... _I>
623 decltype(
auto) apply_impl( _Function&& f
624 , std::optional<Error> e
626 , std::index_sequence<_I...> )
628 return std::forward<_Function>(f)(std::move(e), std::get<_I>(std::forward<_Tuple>(t))...);
633 template <
class _Function,
class _Tuple, std::size_t... _I>
634 constexpr decltype(
auto) apply_impl( _Function&& f
636 , std::index_sequence<_I...> )
638 if constexpr (!std::is_void_v<function_result_t<_Function>>)
639 return std::forward<_Function>(f)(std::get<_I>(std::forward<_Tuple>(t))...);
641 return std::forward<_Function>(f)(std::get<_I>(std::forward<_Tuple>(t))...), std::tuple<>{};
647 template <
class _Function,
class _Tuple>
648 constexpr decltype(
auto) apply(_Function&& f, _Tuple&& t)
650 return detail::apply_impl( std::forward<_Function>(f)
651 , std::forward<_Tuple>(t)
652 , std::make_index_sequence<std::tuple_size<std::decay_t<_Tuple>>::value>{} );
657 template <
class _Function,
class _Tuple,
typename... _Args>
658 constexpr decltype(
auto) apply(_Function&& f, Result<_Args...>&& r, _Tuple&& t)
660 return detail::apply_impl( std::forward<_Function>(f)
662 , std::forward<_Tuple>(t)
663 , std::make_index_sequence<std::tuple_size<std::decay_t<_Tuple>>::value>{} );
668 template <
class _Function,
class _Tuple>
669 decltype(
auto) apply(_Function&& f, std::optional<Error> e, _Tuple&& t)
671 return detail::apply_impl( std::forward<_Function>(f)
673 , std::forward<_Tuple>(t)
674 , std::make_index_sequence<std::tuple_size<std::decay_t<_Tuple>>::value>{} );
678 template <
typename _T, std::
size_t _N1, std::
size_t _N2>
679 constexpr std::array<_T, _N1 + _N2> operator+(std::array<_T, _N1> lhs, std::array<_T, _N2> rhs)
681 std::array<_T, _N1 + _N2> result{};
682 std::size_t index = 0;
684 for (
auto& el : lhs) {
685 result[index] = std::move(el);
688 for (
auto& el : rhs) {
689 result[index] = std::move(el);
std::pair< _T1, _T2 > DictEntry
Definition Types.h:402
Definition MethodResult.h:51
Definition TypeTraits.h:97
Definition TypeTraits.h:94
Definition TypeTraits.h:585
Definition TypeTraits.h:107
Definition TypeTraits.h:101
Definition TypeTraits.h:110
Definition TypeTraits.h:91
Definition TypeTraits.h:425
Definition TypeTraits.h:399
Definition TypeTraits.h:387
Definition TypeTraits.h:556
Definition TypeTraits.h:88
Definition TypeTraits.h:543
Definition TypeTraits.h:126
Definition TypeTraits.h:521
Definition TypeTraits.h:104