mirror of
https://github.com/pybind/pybind11.git
synced 2024-11-29 08:32:02 +00:00
Copy-paste-and-specialize copyable_holder_caster<shared_ptr>, move_only_holder_caster<unique_ptr>. No functional changes.
This commit is contained in:
parent
e4d0a55575
commit
5518e01562
@ -828,6 +828,84 @@ protected:
|
||||
holder_type holder;
|
||||
};
|
||||
|
||||
// BAKEIN_WIP
|
||||
template <typename type>
|
||||
struct copyable_holder_caster<type, std::shared_ptr<type>> : public type_caster_base<type> {
|
||||
public:
|
||||
using base = type_caster_base<type>;
|
||||
static_assert(std::is_base_of<base, type_caster<type>>::value,
|
||||
"Holder classes are only supported for custom types");
|
||||
using base::base;
|
||||
using base::cast;
|
||||
using base::typeinfo;
|
||||
using base::value;
|
||||
|
||||
bool load(handle src, bool convert) {
|
||||
return base::template load_impl<copyable_holder_caster<type, std::shared_ptr<type>>>(
|
||||
src, convert);
|
||||
}
|
||||
|
||||
explicit operator type *() { return this->value; }
|
||||
// static_cast works around compiler error with MSVC 17 and CUDA 10.2
|
||||
// see issue #2180
|
||||
explicit operator type &() { return *(static_cast<type *>(this->value)); }
|
||||
explicit operator std::shared_ptr<type> *() { return std::addressof(holder); }
|
||||
explicit operator std::shared_ptr<type> &() { return holder; }
|
||||
|
||||
static handle cast(const std::shared_ptr<type> &src, return_value_policy, handle) {
|
||||
const auto *ptr = holder_helper<std::shared_ptr<type>>::get(src);
|
||||
return type_caster_base<type>::cast_holder(ptr, &src);
|
||||
}
|
||||
|
||||
protected:
|
||||
friend class type_caster_generic;
|
||||
void check_holder_compat() {
|
||||
if (typeinfo->default_holder) {
|
||||
throw cast_error("Unable to load a custom holder type from a default-holder instance");
|
||||
}
|
||||
}
|
||||
|
||||
bool load_value(value_and_holder &&v_h) {
|
||||
if (v_h.holder_constructed()) {
|
||||
value = v_h.value_ptr();
|
||||
holder = v_h.template holder<std::shared_ptr<type>>();
|
||||
return true;
|
||||
}
|
||||
throw cast_error("Unable to cast from non-held to held instance (T& to Holder<T>) "
|
||||
#if !defined(PYBIND11_DETAILED_ERROR_MESSAGES)
|
||||
"(#define PYBIND11_DETAILED_ERROR_MESSAGES or compile in debug mode for "
|
||||
"type information)");
|
||||
#else
|
||||
"of type '"
|
||||
+ type_id<std::shared_ptr<type>>() + "''");
|
||||
#endif
|
||||
}
|
||||
|
||||
template <typename T = std::shared_ptr<type>,
|
||||
detail::enable_if_t<!std::is_constructible<T, const T &, type *>::value, int> = 0>
|
||||
bool try_implicit_casts(handle, bool) {
|
||||
return false;
|
||||
}
|
||||
|
||||
template <typename T = std::shared_ptr<type>,
|
||||
detail::enable_if_t<std::is_constructible<T, const T &, type *>::value, int> = 0>
|
||||
bool try_implicit_casts(handle src, bool convert) {
|
||||
for (auto &cast : typeinfo->implicit_casts) {
|
||||
copyable_holder_caster sub_caster(*cast.first);
|
||||
if (sub_caster.load(src, convert)) {
|
||||
value = cast.second(sub_caster.value);
|
||||
holder = std::shared_ptr<type>(sub_caster.holder, (type *) value);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
static bool try_direct_conversions(handle) { return false; }
|
||||
|
||||
std::shared_ptr<type> holder;
|
||||
};
|
||||
|
||||
/// Specialize for the common std::shared_ptr, so users don't need to
|
||||
template <typename T>
|
||||
class type_caster<std::shared_ptr<T>> : public copyable_holder_caster<T, std::shared_ptr<T>> {};
|
||||
@ -847,6 +925,19 @@ struct move_only_holder_caster {
|
||||
static constexpr auto name = type_caster_base<type>::name;
|
||||
};
|
||||
|
||||
// BAKEIN_WIP
|
||||
template <typename type, typename deleter>
|
||||
struct move_only_holder_caster<type, std::unique_ptr<type, deleter>> {
|
||||
static_assert(std::is_base_of<type_caster_base<type>, type_caster<type>>::value,
|
||||
"Holder classes are only supported for custom types");
|
||||
|
||||
static handle cast(std::unique_ptr<type, deleter> &&src, return_value_policy, handle) {
|
||||
auto *ptr = src.get();
|
||||
return type_caster_base<type>::cast_holder(ptr, std::addressof(src));
|
||||
}
|
||||
static constexpr auto name = type_caster_base<type>::name;
|
||||
};
|
||||
|
||||
template <typename type, typename deleter>
|
||||
class type_caster<std::unique_ptr<type, deleter>>
|
||||
: public move_only_holder_caster<type, std::unique_ptr<type, deleter>> {};
|
||||
|
Loading…
Reference in New Issue
Block a user