mirror of
https://github.com/pybind/pybind11.git
synced 2024-11-22 05:05:11 +00:00
address issue with std::type_info across module boundaries (fixes #86)
This commit is contained in:
parent
2547ca468c
commit
b6cf75d66a
@ -59,20 +59,9 @@ PYBIND11_NOINLINE inline detail::type_info* get_type_info(PyTypeObject *type) {
|
||||
PYBIND11_NOINLINE inline detail::type_info *get_type_info(const std::type_info &tp) {
|
||||
auto &types = get_internals().registered_types_cpp;
|
||||
|
||||
auto it = types.find(&tp);
|
||||
if (it != types.end()) {
|
||||
auto it = types.find(std::type_index(tp));
|
||||
if (it != types.end())
|
||||
return (detail::type_info *) it->second;
|
||||
} else {
|
||||
/* Unknown type?! Since std::type_info* often varies across
|
||||
module boundaries, the following does an explicit check */
|
||||
for (auto const &type : types) {
|
||||
auto *first = (const std::type_info *) type.first;
|
||||
if (strcmp(first->name(), tp.name()) == 0) {
|
||||
types[&tp] = type.second;
|
||||
return (detail::type_info *) type.second;
|
||||
}
|
||||
}
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
@ -144,7 +133,7 @@ public:
|
||||
if (it_instance != internals.registered_instances.end() && !dont_cache)
|
||||
return handle((PyObject *) it_instance->second).inc_ref();
|
||||
|
||||
auto it = internals.registered_types_cpp.find(type_info);
|
||||
auto it = internals.registered_types_cpp.find(std::type_index(*type_info));
|
||||
if (it == internals.registered_types_cpp.end()) {
|
||||
std::string tname = type_info->name();
|
||||
detail::clean_type_id(tname);
|
||||
|
@ -71,6 +71,7 @@
|
||||
#include <unordered_set>
|
||||
#include <unordered_map>
|
||||
#include <memory>
|
||||
#include <typeindex>
|
||||
|
||||
#if PY_MAJOR_VERSION >= 3 /// Compatibility macros for various Python versions
|
||||
#define PYBIND11_INSTANCE_METHOD_NEW(ptr, class_) PyInstanceMethod_New(ptr)
|
||||
@ -216,9 +217,9 @@ struct overload_hash {
|
||||
|
||||
/// Internal data struture used to track registered instances and types
|
||||
struct internals {
|
||||
std::unordered_map<const void *, void*> registered_types_cpp; // std::type_info* -> type_info
|
||||
std::unordered_map<const void *, void*> registered_types_py; // PyTypeObject* -> type_info
|
||||
std::unordered_map<const void *, void*> registered_instances; // void * -> PyObject*
|
||||
std::unordered_map<std::type_index, void*> registered_types_cpp; // std::type_index -> type_info
|
||||
std::unordered_map<const void *, void*> registered_types_py; // PyTypeObject* -> type_info
|
||||
std::unordered_map<const void *, void*> registered_instances; // void * -> PyObject*
|
||||
std::unordered_set<std::pair<const PyObject *, const char *>, overload_hash> inactive_overload_cache;
|
||||
};
|
||||
|
||||
|
@ -204,7 +204,7 @@ protected:
|
||||
const std::type_info *t = types[type_index++];
|
||||
if (!t)
|
||||
pybind11_fail("Internal error while parsing type signature (1)");
|
||||
auto it = registered_types.find(t);
|
||||
auto it = registered_types.find(std::type_index(*t));
|
||||
if (it != registered_types.end()) {
|
||||
signature += ((const detail::type_info *) it->second)->type->tp_name;
|
||||
} else {
|
||||
@ -524,7 +524,7 @@ protected:
|
||||
tinfo->type = (PyTypeObject *) type;
|
||||
tinfo->type_size = rec->type_size;
|
||||
tinfo->init_holder = rec->init_holder;
|
||||
internals.registered_types_cpp[rec->type] = tinfo;
|
||||
internals.registered_types_cpp[std::type_index(*(rec->type))] = tinfo;
|
||||
internals.registered_types_py[type] = tinfo;
|
||||
|
||||
auto scope_module = (object) rec->scope.attr("__module__");
|
||||
@ -844,7 +844,7 @@ public:
|
||||
|
||||
template <typename target> class_ alias() {
|
||||
auto &instances = pybind11::detail::get_internals().registered_types_cpp;
|
||||
instances[&typeid(target)] = instances[&typeid(type)];
|
||||
instances[std::type_index(typeid(target))] = instances[std::type_index(typeid(type))];
|
||||
return *this;
|
||||
}
|
||||
private:
|
||||
@ -976,8 +976,8 @@ template <typename InputType, typename OutputType> void implicitly_convertible()
|
||||
PyErr_Clear();
|
||||
return result;
|
||||
};
|
||||
auto & registered_types = detail::get_internals().registered_types_cpp;
|
||||
auto it = registered_types.find(&typeid(OutputType));
|
||||
auto ®istered_types = detail::get_internals().registered_types_cpp;
|
||||
auto it = registered_types.find(std::type_index(typeid(OutputType)));
|
||||
if (it == registered_types.end())
|
||||
pybind11_fail("implicitly_convertible: Unable to find type " + type_id<OutputType>());
|
||||
((detail::type_info *) it->second)->implicit_conversions.push_back(implicit_caster);
|
||||
|
Loading…
Reference in New Issue
Block a user