diff options
Diffstat (limited to 'src/boost/libs/python/test/m1.cpp')
-rw-r--r-- | src/boost/libs/python/test/m1.cpp | 344 |
1 files changed, 344 insertions, 0 deletions
diff --git a/src/boost/libs/python/test/m1.cpp b/src/boost/libs/python/test/m1.cpp new file mode 100644 index 000000000..a873bc35d --- /dev/null +++ b/src/boost/libs/python/test/m1.cpp @@ -0,0 +1,344 @@ +// Copyright David Abrahams 2001. +// Distributed under the Boost Software License, Version 1.0. (See +// accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + + +#include <boost/python/def.hpp> +#include <boost/python/module.hpp> +#include <boost/python/class.hpp> +#include <boost/python/lvalue_from_pytype.hpp> +#include <boost/python/copy_const_reference.hpp> +#include <boost/python/return_value_policy.hpp> +#include <boost/python/to_python_converter.hpp> +#include <boost/python/errors.hpp> +#include <boost/python/manage_new_object.hpp> +#include <boost/python/converter/pytype_function.hpp> +#include <string.h> +#include "simple_type.hpp" +#include "complicated.hpp" + +// Declare some straightforward extension types +extern "C" void +dealloc(PyObject* self) +{ + PyObject_Del(self); +} + +// Noddy is a type we got from one of the Python sample files +struct NoddyObject : PyObject +{ + int x; +}; + +PyTypeObject NoddyType = { + PyVarObject_HEAD_INIT(NULL, 0) + const_cast<char*>("Noddy"), + sizeof(NoddyObject), + 0, + dealloc, /* tp_dealloc */ + 0, /* tp_print */ + 0, /* tp_getattr */ + 0, /* tp_setattr */ + 0, /* tp_compare */ + 0, /* tp_repr */ + 0, /* tp_as_number */ + 0, /* tp_as_sequence */ + 0, /* tp_as_mapping */ + 0, /* tp_hash */ + 0, /* tp_call */ + 0, /* tp_str */ + 0, /* tp_getattro */ + 0, /* tp_setattro */ + 0, /* tp_as_buffer */ + 0, /* tp_flags */ + 0, /* tp_doc */ + 0, /* tp_traverse */ + 0, /* tp_clear */ + 0, /* tp_richcompare */ + 0, /* tp_weaklistoffset */ + 0, /* tp_iter */ + 0, /* tp_iternext */ + 0, /* tp_methods */ + 0, /* tp_members */ + 0, /* tp_getset */ + 0, /* tp_base */ + 0, /* tp_dict */ + 0, /* tp_descr_get */ + 0, /* tp_descr_set */ + 0, /* tp_dictoffset */ + 0, /* tp_init */ + 0, /* tp_alloc */ + 0, /* tp_new */ + 0, /* tp_free */ + 0, /* tp_is_gc */ + 0, /* tp_bases */ + 0, /* tp_mro */ + 0, /* tp_cache */ + 0, /* tp_subclasses */ + 0, /* tp_weaklist */ +#if PYTHON_API_VERSION >= 1012 + 0 /* tp_del */ +#endif +}; + +// Create a Noddy containing 42 +PyObject* new_noddy() +{ + NoddyObject* noddy = PyObject_New(NoddyObject, &NoddyType); + noddy->x = 42; + return (PyObject*)noddy; +} + +// Simple is a wrapper around a struct simple, which just contains a char* +struct SimpleObject +{ + PyObject_HEAD + simple x; +}; + +struct extract_simple_object +{ + static simple& execute(SimpleObject& o) { return o.x; } +}; + +PyTypeObject SimpleType = { + PyVarObject_HEAD_INIT(NULL, 0) + const_cast<char*>("Simple"), + sizeof(SimpleObject), + 0, + dealloc, /* tp_dealloc */ + 0, /* tp_print */ + 0, /* tp_getattr */ + 0, /* tp_setattr */ + 0, /* tp_compare */ + 0, /* tp_repr */ + 0, /* tp_as_number */ + 0, /* tp_as_sequence */ + 0, /* tp_as_mapping */ + 0, /* tp_hash */ + 0, /* tp_call */ + 0, /* tp_str */ + 0, /* tp_getattro */ + 0, /* tp_setattro */ + 0, /* tp_as_buffer */ + 0, /* tp_flags */ + 0, /* tp_doc */ + 0, /* tp_traverse */ + 0, /* tp_clear */ + 0, /* tp_richcompare */ + 0, /* tp_weaklistoffset */ + 0, /* tp_iter */ + 0, /* tp_iternext */ + 0, /* tp_methods */ + 0, /* tp_members */ + 0, /* tp_getset */ + 0, /* tp_base */ + 0, /* tp_dict */ + 0, /* tp_descr_get */ + 0, /* tp_descr_set */ + 0, /* tp_dictoffset */ + 0, /* tp_init */ + 0, /* tp_alloc */ + 0, /* tp_new */ + 0, /* tp_free */ + 0, /* tp_is_gc */ + 0, /* tp_bases */ + 0, /* tp_mro */ + 0, /* tp_cache */ + 0, /* tp_subclasses */ + 0, /* tp_weaklist */ +#if PYTHON_API_VERSION >= 1012 + 0 /* tp_del */ +#endif +}; + +// Create a Simple containing "hello, world" +PyObject* new_simple() +{ + SimpleObject* simple = PyObject_New(SimpleObject, &SimpleType); + simple->x.s = const_cast<char*>("hello, world"); + return (PyObject*)simple; +} + +// +// Declare some wrappers/unwrappers to test the low-level conversion +// mechanism. +// +using boost::python::to_python_converter; + +// Wrap a simple by copying it into a Simple +struct simple_to_python + : to_python_converter<simple, simple_to_python, true> + //, boost::python::converter::wrap_pytype<&SimpleType> +{ + static PyObject* convert(simple const& x) + { + SimpleObject* p = PyObject_New(SimpleObject, &SimpleType); + p->x = x; + return (PyObject*)p; + } + static PyTypeObject const *get_pytype(){return &SimpleType; } +}; + +struct int_from_noddy +{ + static int& execute(NoddyObject& p) + { + return p.x; + } +}; + +// +// Some C++ functions to expose to Python +// + +// Returns the length of s's held string +int f(simple const& s) +{ + return strlen(s.s); +} + +int f_mutable_ref(simple& s) +{ + return strlen(s.s); +} + +int f_mutable_ptr(simple* s) +{ + return strlen(s->s); +} + +int f_const_ptr(simple const* s) +{ + return strlen(s->s); +} + +int f2(SimpleObject const& s) +{ + return strlen(s.x.s); +} + +// A trivial passthru function for simple objects +simple const& g(simple const& x) +{ + return x; +} + +struct A +{ + A() : x(0) {} + virtual ~A() {} + char const* name() { return "A"; } + int x; +}; + +struct B : A +{ + B() : x(1) {} + static char const* name(B*) { return "B"; } + int x; +}; + +struct C : A +{ + C() : x(2) {} + char const* name() { return "C"; } + virtual ~C() {} + int x; +}; + +struct D : B, C +{ + D() : x(3) {} + char const* name() { return "D"; } + int x; +}; + +A take_a(A const& a) { return a; } +B take_b(B& b) { return b; } +C take_c(C* c) { return *c; } +D take_d(D* const& d) { return *d; } + +D take_d_shared_ptr(boost::shared_ptr<D> d) { return *d; } + +boost::shared_ptr<A> d_factory() { return boost::shared_ptr<B>(new D); } + +struct Unregistered {}; +Unregistered make_unregistered(int) { return Unregistered(); } + +Unregistered* make_unregistered2(int) { return new Unregistered; } + +BOOST_PYTHON_MODULE(m1) +{ + using namespace boost::python; + using boost::shared_ptr; + + simple_to_python(); + + lvalue_from_pytype<int_from_noddy,&NoddyType>(); + + lvalue_from_pytype< +#if !defined(BOOST_MSVC) || BOOST_MSVC > 1300 // doesn't support non-type member pointer parameters + extract_member<SimpleObject, simple, &SimpleObject::x> +#else + extract_simple_object +#endif + , &SimpleType + >(); + + lvalue_from_pytype<extract_identity<SimpleObject>,&SimpleType>(); + + def("new_noddy", new_noddy); + def("new_simple", new_simple); + + def("make_unregistered", make_unregistered); + def("make_unregistered2", make_unregistered2, return_value_policy<manage_new_object>()); + + // Expose f() in all its variations + def("f", f); + def("f_mutable_ref", f_mutable_ref); + def("f_mutable_ptr", f_mutable_ptr); + def("f_const_ptr", f_const_ptr); + + def("f2", f2); + + // Expose g() + def("g", g , return_value_policy<copy_const_reference>() + ); + + def("take_a", take_a); + def("take_b", take_b); + def("take_c", take_c); + def("take_d", take_d); + + + def("take_d_shared_ptr", take_d_shared_ptr); + def("d_factory", d_factory); + + class_<A, shared_ptr<A> >("A") + .def("name", &A::name) + ; + + // sequence points don't ensure that "A" is constructed before "B" + // or "C" below if we make them part of the same chain + class_<B,bases<A> >("B") + .def("name", &B::name) + ; + + class_<C,bases<A> >("C") + .def("name", &C::name) + ; + + class_<D, bases<B,C> >("D") + .def("name", &D::name) + ; + + class_<complicated>("complicated", + init<simple const&,int>()) + .def(init<simple const&>()) + .def("get_n", &complicated::get_n) + ; +} + +#include "module_tail.cpp" |