source: NonGTP/Boost/boost/python/lvalue_from_pytype.hpp @ 857

Revision 857, 3.3 KB checked in by igarcia, 18 years ago (diff)
Line 
1// Copyright David Abrahams 2002.
2// Distributed under the Boost Software License, Version 1.0. (See
3// accompanying file LICENSE_1_0.txt or copy at
4// http://www.boost.org/LICENSE_1_0.txt)
5#ifndef LVALUE_FROM_PYTYPE_DWA2002130_HPP
6# define LVALUE_FROM_PYTYPE_DWA2002130_HPP
7
8# include <boost/python/detail/prefix.hpp>
9
10# include <boost/python/type_id.hpp>
11# include <boost/python/converter/registry.hpp>
12# include <boost/python/detail/void_ptr.hpp>
13
14namespace boost { namespace python {
15
16namespace detail
17{
18  // Given a pointer-to-function of 1 parameter returning a reference
19  // type, return the type_id of the function's return type.
20  template <class T, class U>
21  inline type_info extractor_type_id(T&(*)(U))
22  {
23      return type_id<T>();
24  }
25
26  // A function generator whose static execute() function is an lvalue
27  // from_python converter using the given Extractor. U is expected to
28  // be the actual type of the PyObject instance from which the result
29  // is being extracted.
30  template <class Extractor, class U>
31  struct normalized_extractor
32  {
33      static inline void* execute(PyObject* op)
34      {
35          typedef typename boost::add_reference<U>::type param;
36          return &Extractor::execute(
37              boost::python::detail::void_ptr_to_reference(
38                  op, (param(*)())0 )
39              );
40      }
41  };
42
43  // Given an Extractor type and a pointer to its execute function,
44  // return a new object whose static execute function does the same
45  // job but is a conforming lvalue from_python conversion function.
46  //
47  // usage: normalize<Extractor>(&Extractor::execute)
48  template <class Extractor, class T, class U>
49  inline normalized_extractor<Extractor,U>
50  normalize(T(*)(U), Extractor* = 0)
51  {
52      return normalized_extractor<Extractor, U>();
53  }
54}
55
56// An Extractor which extracts the given member from a Python object
57// whose instances are stored as InstanceType.
58template <class InstanceType, class MemberType, MemberType (InstanceType::*member)>
59struct extract_member
60{
61    static MemberType& execute(InstanceType& c)
62    {
63        (void)c.ob_type; // static assertion
64        return c.*member;
65    }
66};
67
68// An Extractor which simply extracts the entire python object
69// instance of InstanceType.
70template <class InstanceType>
71struct extract_identity
72{
73    static InstanceType& execute(InstanceType& c)
74    {
75        (void)c.ob_type; // static assertion
76        return c;
77    }
78};
79
80// Registers a from_python conversion which extracts lvalues using
81// Extractor's static execute function from Python objects whose type
82// object is python_type.
83template <class Extractor, PyTypeObject const* python_type>
84struct lvalue_from_pytype
85{
86    lvalue_from_pytype()
87    {
88        converter::registry::insert(
89            &extract, detail::extractor_type_id(&Extractor::execute));
90    }
91 private:
92    static void* extract(PyObject* op)
93    {
94        return PyObject_TypeCheck(op, const_cast<PyTypeObject*>(python_type))
95            ? const_cast<void*>(
96                static_cast<void const volatile*>(
97                    detail::normalize<Extractor>(&Extractor::execute).execute(op)))
98            : 0
99            ;
100    }
101};
102
103}} // namespace boost::python
104
105#endif // LVALUE_FROM_PYTYPE_DWA2002130_HPP
Note: See TracBrowser for help on using the repository browser.