From 819cb5533ed8e1654a11e2defc6cd1ea8254ab86 Mon Sep 17 00:00:00 2001 From: Dean Moldovan Date: Wed, 15 Mar 2017 13:57:10 +0100 Subject: [PATCH] Fix nullptr to None conversion for builtin type casters Fixes #731. Generally, this applies to any caster made with PYBIND11_TYPE_CASTER(). --- include/pybind11/cast.h | 1 + tests/test_python_types.cpp | 6 ++++++ tests/test_python_types.py | 11 +++++++++++ 3 files changed, 18 insertions(+) diff --git a/include/pybind11/cast.h b/include/pybind11/cast.h index b8638b9c2..94d3e03b5 100644 --- a/include/pybind11/cast.h +++ b/include/pybind11/cast.h @@ -469,6 +469,7 @@ public: public: \ static PYBIND11_DESCR name() { return type_descr(py_name); } \ static handle cast(const type *src, return_value_policy policy, handle parent) { \ + if (!src) return none().release(); \ return cast(*src, policy, parent); \ } \ operator type*() { return &value; } \ diff --git a/tests/test_python_types.cpp b/tests/test_python_types.cpp index 6a0044ca3..399129fad 100644 --- a/tests/test_python_types.cpp +++ b/tests/test_python_types.cpp @@ -464,6 +464,12 @@ test_initializer python_types([](py::module &m) { m.def("ord_char16", [](char16_t c) -> uint16_t { return c; }); m.def("ord_char32", [](char32_t c) -> uint32_t { return c; }); m.def("ord_wchar", [](wchar_t c) -> int { return c; }); + + m.def("return_none_string", []() -> std::string * { return nullptr; }); + m.def("return_none_char", []() -> const char * { return nullptr; }); + m.def("return_none_bool", []() -> bool * { return nullptr; }); + m.def("return_none_int", []() -> int * { return nullptr; }); + m.def("return_none_float", []() -> float * { return nullptr; }); }); #if defined(_MSC_VER) diff --git a/tests/test_python_types.py b/tests/test_python_types.py index cf5412dfa..7ca020e89 100644 --- a/tests/test_python_types.py +++ b/tests/test_python_types.py @@ -501,3 +501,14 @@ def test_single_char_arguments(): with pytest.raises(ValueError) as excinfo: assert ord_wchar(u'aa') assert str(excinfo.value) == toolong_message + + +def test_builtins_cast_return_none(): + """Casters produced with PYBIND11_TYPE_CASTER() should convert nullptr to None""" + import pybind11_tests as m + + assert m.return_none_string() is None + assert m.return_none_char() is None + assert m.return_none_bool() is None + assert m.return_none_int() is None + assert m.return_none_float() is None