@@ -33,6 +33,35 @@ using provider_unique_handle_t =
33
33
std::unique_ptr<umf_memory_provider_t ,
34
34
std::function<void (umf_memory_provider_handle_t )>>;
35
35
36
+ #define DEFINE_CHECK_OP (op ) \
37
+ template <typename T> class HAS_OP_ ##op { \
38
+ typedef char check_success; \
39
+ typedef long check_fail; \
40
+ template <typename U> static check_success test (decltype (&U::op)); \
41
+ template <typename U> static check_fail test (...); \
42
+ \
43
+ public: \
44
+ static constexpr bool value = \
45
+ sizeof (test<T>(0 )) == sizeof (check_success); \
46
+ }; \
47
+ \
48
+ template <typename T, typename ... Args> \
49
+ static inline \
50
+ typename std::enable_if<HAS_OP_##op<T>::value, umf_result_t >::type \
51
+ CALL_OP_##op(T *t, Args &&...args) { \
52
+ return t->op (std::forward<Args>(args)...); \
53
+ }; \
54
+ \
55
+ static inline umf_result_t CALL_OP_##op(...) { \
56
+ return UMF_RESULT_ERROR_NOT_SUPPORTED; \
57
+ }
58
+
59
+ DEFINE_CHECK_OP (get_ipc_handle_size);
60
+ DEFINE_CHECK_OP (get_ipc_handle);
61
+ DEFINE_CHECK_OP (put_ipc_handle);
62
+ DEFINE_CHECK_OP (open_ipc_handle);
63
+ DEFINE_CHECK_OP (close_ipc_handle);
64
+
36
65
#define UMF_ASSIGN_OP (ops, type, func, default_return ) \
37
66
ops.func = [](void *obj, auto ... args) { \
38
67
try { \
@@ -50,6 +79,15 @@ using provider_unique_handle_t =
50
79
} \
51
80
}
52
81
82
+ #define UMF_ASSIGN_OP_OPT (ops, type, func, default_return ) \
83
+ ops.func = [](void *obj, auto ... args) { \
84
+ try { \
85
+ return CALL_OP_##func (reinterpret_cast <type *>(obj), args...); \
86
+ } catch (...) { \
87
+ return default_return; \
88
+ } \
89
+ }
90
+
53
91
namespace detail {
54
92
template <typename T, typename ArgsTuple>
55
93
umf_result_t initialize (T *obj, ArgsTuple &&args) {
@@ -133,6 +171,12 @@ auto memoryProviderMakeUnique(Args &&...args) {
133
171
UMF_ASSIGN_OP (ops.ext , T, purge_force, UMF_RESULT_ERROR_UNKNOWN);
134
172
UMF_ASSIGN_OP (ops.ext , T, allocation_merge, UMF_RESULT_ERROR_UNKNOWN);
135
173
UMF_ASSIGN_OP (ops.ext , T, allocation_split, UMF_RESULT_ERROR_UNKNOWN);
174
+ UMF_ASSIGN_OP_OPT (ops.ipc , T, get_ipc_handle_size,
175
+ UMF_RESULT_ERROR_UNKNOWN);
176
+ UMF_ASSIGN_OP_OPT (ops.ipc , T, get_ipc_handle, UMF_RESULT_ERROR_UNKNOWN);
177
+ UMF_ASSIGN_OP_OPT (ops.ipc , T, put_ipc_handle, UMF_RESULT_ERROR_UNKNOWN);
178
+ UMF_ASSIGN_OP_OPT (ops.ipc , T, open_ipc_handle, UMF_RESULT_ERROR_UNKNOWN);
179
+ UMF_ASSIGN_OP_OPT (ops.ipc , T, close_ipc_handle, UMF_RESULT_ERROR_UNKNOWN);
136
180
137
181
umf_memory_provider_handle_t hProvider = nullptr ;
138
182
auto ret = umfMemoryProviderCreate (&ops, &argsTuple, &hProvider);
0 commit comments