Scarab  v2.9.1
Project 8 C++ Utility Library
attr.h
Go to the documentation of this file.
1 /*
2  pybind11/attr.h: Infrastructure for processing custom
3  type and function attributes
4 
5  Copyright (c) 2016 Wenzel Jakob <wenzel.jakob@epfl.ch>
6 
7  All rights reserved. Use of this source code is governed by a
8  BSD-style license that can be found in the LICENSE file.
9 */
10 
11 #pragma once
12 
13 #include "cast.h"
14 
16 
17 
21 struct is_method { handle class_; is_method(const handle &c) : class_(c) { } };
22 
24 struct is_operator { };
25 
27 struct scope { handle value; scope(const handle &s) : value(s) { } };
28 
30 struct doc { const char *value; doc(const char *value) : value(value) { } };
31 
33 struct name { const char *value; name(const char *value) : value(value) { } };
34 
36 struct sibling { handle value; sibling(const handle &value) : value(value.ptr()) { } };
37 
39 template <typename T> struct base {
40  PYBIND11_DEPRECATED("base<T>() was deprecated in favor of specifying 'T' as a template argument to class_")
41  base() { }
42 };
43 
45 template <size_t Nurse, size_t Patient> struct keep_alive { };
46 
49 
51 struct dynamic_attr { };
52 
54 struct buffer_protocol { };
55 
57 struct metaclass {
59 
60  PYBIND11_DEPRECATED("py::metaclass() is no longer required. It's turned on by default now.")
61  metaclass() {}
62 
64  explicit metaclass(handle value) : value(value) { }
65 };
66 
68 struct module_local { const bool value; constexpr module_local(bool v = true) : value(v) { } };
69 
71 struct arithmetic { };
72 
91 template <typename... Ts> struct call_guard;
92 
93 template <> struct call_guard<> { using type = detail::void_type; };
94 
95 template <typename T>
96 struct call_guard<T> {
98  "The guard type must be default constructible");
99 
100  using type = T;
101 };
102 
103 template <typename T, typename... Ts>
104 struct call_guard<T, Ts...> {
105  struct type {
106  T guard{}; // Compose multiple guard types with left-to-right default-constructor order
107  typename call_guard<Ts...>::type next{};
108  };
109 };
110 
112 
114 /* Forward declarations */
115 enum op_id : int;
116 enum op_type : int;
117 struct undefined_t;
118 template <op_id id, op_type ot, typename L = undefined_t, typename R = undefined_t> struct op_;
119 inline void keep_alive_impl(size_t Nurse, size_t Patient, function_call &call, handle ret);
120 
123  const char *name;
124  const char *descr;
126  bool convert : 1;
127  bool none : 1;
128 
129  argument_record(const char *name, const char *descr, handle value, bool convert, bool none)
130  : name(name), descr(descr), value(value), convert(convert), none(none) { }
131 };
132 
136  : is_constructor(false), is_new_style_constructor(false), is_stateless(false),
137  is_operator(false), has_args(false), has_kwargs(false), is_method(false) { }
138 
140  char *name = nullptr; /* why no C++ strings? They generate heavier code.. */
141 
142  // User-specified documentation string
143  char *doc = nullptr;
144 
146  char *signature = nullptr;
147 
149  std::vector<argument_record> args;
150 
152  handle (*impl) (function_call &) = nullptr;
153 
155  void *data[3] = { };
156 
158  void (*free_data) (function_record *ptr) = nullptr;
159 
161  return_value_policy policy = return_value_policy::automatic;
162 
164  bool is_constructor : 1;
165 
168 
170  bool is_stateless : 1;
171 
173  bool is_operator : 1;
174 
176  bool has_args : 1;
177 
179  bool has_kwargs : 1;
180 
182  bool is_method : 1;
183 
185  std::uint16_t nargs;
186 
188  PyMethodDef *def = nullptr;
189 
192 
195 
197  function_record *next = nullptr;
198 };
199 
201 struct type_record {
203  : multiple_inheritance(false), dynamic_attr(false), buffer_protocol(false),
204  default_holder(true), module_local(false) { }
205 
208 
210  const char *name = nullptr;
211 
212  // Pointer to RTTI type_info data structure
213  const std::type_info *type = nullptr;
214 
216  size_t type_size = 0;
217 
219  size_t type_align = 0;
220 
222  size_t holder_size = 0;
223 
225  void *(*operator_new)(size_t) = nullptr;
226 
228  void (*init_instance)(instance *, const void *) = nullptr;
229 
231  void (*dealloc)(detail::value_and_holder &) = nullptr;
232 
235 
237  const char *doc = nullptr;
238 
241 
244 
246  bool dynamic_attr : 1;
247 
249  bool buffer_protocol : 1;
250 
252  bool default_holder : 1;
253 
255  bool module_local : 1;
256 
257  PYBIND11_NOINLINE void add_base(const std::type_info &base, void *(*caster)(void *)) {
258  auto base_info = detail::get_type_info(base, false);
259  if (!base_info) {
260  std::string tname(base.name());
261  detail::clean_type_id(tname);
262  pybind11_fail("generic_type: type \"" + std::string(name) +
263  "\" referenced unknown base type \"" + tname + "\"");
264  }
265 
266  if (default_holder != base_info->default_holder) {
267  std::string tname(base.name());
268  detail::clean_type_id(tname);
269  pybind11_fail("generic_type: type \"" + std::string(name) + "\" " +
270  (default_holder ? "does not have" : "has") +
271  " a non-default holder type while its base \"" + tname + "\" " +
272  (base_info->default_holder ? "does not" : "does"));
273  }
274 
275  bases.append((PyObject *) base_info->type);
276 
277  if (base_info->type->tp_dictoffset != 0)
278  dynamic_attr = true;
279 
280  if (caster)
281  base_info->implicit_casts.emplace_back(type, caster);
282  }
283 };
284 
285 inline function_call::function_call(const function_record &f, handle p) :
286  func(f), parent(p) {
287  args.reserve(f.nargs);
288  args_convert.reserve(f.nargs);
289 }
290 
293 
300 template <typename T, typename SFINAE = void> struct process_attribute;
301 
302 template <typename T> struct process_attribute_default {
304  static void init(const T &, function_record *) { }
305  static void init(const T &, type_record *) { }
306  static void precall(function_call &) { }
307  static void postcall(function_call &, handle) { }
308 };
309 
311 template <> struct process_attribute<name> : process_attribute_default<name> {
312  static void init(const name &n, function_record *r) { r->name = const_cast<char *>(n.value); }
313 };
314 
316 template <> struct process_attribute<doc> : process_attribute_default<doc> {
317  static void init(const doc &n, function_record *r) { r->doc = const_cast<char *>(n.value); }
318 };
319 
321 template <> struct process_attribute<const char *> : process_attribute_default<const char *> {
322  static void init(const char *d, function_record *r) { r->doc = const_cast<char *>(d); }
323  static void init(const char *d, type_record *r) { r->doc = const_cast<char *>(d); }
324 };
325 template <> struct process_attribute<char *> : process_attribute<const char *> { };
326 
328 template <> struct process_attribute<return_value_policy> : process_attribute_default<return_value_policy> {
329  static void init(const return_value_policy &p, function_record *r) { r->policy = p; }
330 };
331 
333 template <> struct process_attribute<sibling> : process_attribute_default<sibling> {
334  static void init(const sibling &s, function_record *r) { r->sibling = s.value; }
335 };
336 
338 template <> struct process_attribute<is_method> : process_attribute_default<is_method> {
339  static void init(const is_method &s, function_record *r) { r->is_method = true; r->scope = s.class_; }
340 };
341 
343 template <> struct process_attribute<scope> : process_attribute_default<scope> {
344  static void init(const scope &s, function_record *r) { r->scope = s.value; }
345 };
346 
348 template <> struct process_attribute<is_operator> : process_attribute_default<is_operator> {
349  static void init(const is_operator &, function_record *r) { r->is_operator = true; }
350 };
351 
352 template <> struct process_attribute<is_new_style_constructor> : process_attribute_default<is_new_style_constructor> {
354 };
355 
357 template <> struct process_attribute<arg> : process_attribute_default<arg> {
358  static void init(const arg &a, function_record *r) {
359  if (r->is_method && r->args.empty())
360  r->args.emplace_back("self", nullptr, handle(), true /*convert*/, false /*none not allowed*/);
361  r->args.emplace_back(a.name, nullptr, handle(), !a.flag_noconvert, a.flag_none);
362  }
363 };
364 
366 template <> struct process_attribute<arg_v> : process_attribute_default<arg_v> {
367  static void init(const arg_v &a, function_record *r) {
368  if (r->is_method && r->args.empty())
369  r->args.emplace_back("self", nullptr /*descr*/, handle() /*parent*/, true /*convert*/, false /*none not allowed*/);
370 
371  if (!a.value) {
372 #if !defined(NDEBUG)
373  std::string descr("'");
374  if (a.name) descr += std::string(a.name) + ": ";
375  descr += a.type + "'";
376  if (r->is_method) {
377  if (r->name)
378  descr += " in method '" + (std::string) str(r->scope) + "." + (std::string) r->name + "'";
379  else
380  descr += " in method of '" + (std::string) str(r->scope) + "'";
381  } else if (r->name) {
382  descr += " in function '" + (std::string) r->name + "'";
383  }
384  pybind11_fail("arg(): could not convert default argument "
385  + descr + " into a Python object (type not registered yet?)");
386 #else
387  pybind11_fail("arg(): could not convert default argument "
388  "into a Python object (type not registered yet?). "
389  "Compile in debug mode for more information.");
390 #endif
391  }
392  r->args.emplace_back(a.name, a.descr, a.value.inc_ref(), !a.flag_noconvert, a.flag_none);
393  }
394 };
395 
397 template <typename T>
399  static void init(const handle &h, type_record *r) { r->bases.append(h); }
400 };
401 
403 template <typename T>
404 struct process_attribute<base<T>> : process_attribute_default<base<T>> {
405  static void init(const base<T> &, type_record *r) { r->add_base(typeid(T), nullptr); }
406 };
407 
409 template <>
411  static void init(const multiple_inheritance &, type_record *r) { r->multiple_inheritance = true; }
412 };
413 
414 template <>
416  static void init(const dynamic_attr &, type_record *r) { r->dynamic_attr = true; }
417 };
418 
419 template <>
421  static void init(const buffer_protocol &, type_record *r) { r->buffer_protocol = true; }
422 };
423 
424 template <>
425 struct process_attribute<metaclass> : process_attribute_default<metaclass> {
426  static void init(const metaclass &m, type_record *r) { r->metaclass = m.value; }
427 };
428 
429 template <>
431  static void init(const module_local &l, type_record *r) { r->module_local = l.value; }
432 };
433 
435 template <>
437 
438 template <typename... Ts>
439 struct process_attribute<call_guard<Ts...>> : process_attribute_default<call_guard<Ts...>> { };
440 
446 template <size_t Nurse, size_t Patient> struct process_attribute<keep_alive<Nurse, Patient>> : public process_attribute_default<keep_alive<Nurse, Patient>> {
447  template <size_t N = Nurse, size_t P = Patient, enable_if_t<N != 0 && P != 0, int> = 0>
448  static void precall(function_call &call) { keep_alive_impl(Nurse, Patient, call, handle()); }
449  template <size_t N = Nurse, size_t P = Patient, enable_if_t<N != 0 && P != 0, int> = 0>
450  static void postcall(function_call &, handle) { }
451  template <size_t N = Nurse, size_t P = Patient, enable_if_t<N == 0 || P == 0, int> = 0>
452  static void precall(function_call &) { }
453  template <size_t N = Nurse, size_t P = Patient, enable_if_t<N == 0 || P == 0, int> = 0>
454  static void postcall(function_call &call, handle ret) { keep_alive_impl(Nurse, Patient, call, ret); }
455 };
456 
458 template <typename... Args> struct process_attributes {
459  static void init(const Args&... args, function_record *r) {
460  int unused[] = { 0, (process_attribute<typename std::decay<Args>::type>::init(args, r), 0) ... };
461  ignore_unused(unused);
462  }
463  static void init(const Args&... args, type_record *r) {
464  int unused[] = { 0, (process_attribute<typename std::decay<Args>::type>::init(args, r), 0) ... };
465  ignore_unused(unused);
466  }
467  static void precall(function_call &call) {
468  int unused[] = { 0, (process_attribute<typename std::decay<Args>::type>::precall(call), 0) ... };
469  ignore_unused(unused);
470  }
471  static void postcall(function_call &call, handle fn_ret) {
472  int unused[] = { 0, (process_attribute<typename std::decay<Args>::type>::postcall(call, fn_ret), 0) ... };
473  ignore_unused(unused);
474  }
475 };
476 
477 template <typename T>
479 
481 template <typename... Extra>
483 
485 template <typename... Extra,
488 constexpr bool expected_num_args(size_t nargs, bool has_args, bool has_kwargs) {
489  return named == 0 || (self + named + has_args + has_kwargs) == nargs;
490 }
491 
492 NAMESPACE_END(detail)
static void init(const dynamic_attr &, type_record *r)
Definition: attr.h:416
Annotation for methods.
Definition: attr.h:21
std::uint16_t nargs
Number of arguments (including py::args and/or py::kwargs, if present)
Definition: attr.h:185
Type for an unused type slot.
Definition: operators.h:44
static void init(const name &n, function_record *r)
Definition: attr.h:312
static void init(const is_new_style_constructor &, function_record *r)
Definition: attr.h:353
bool has_kwargs
True if the function has a &#39;**kwargs&#39; argument.
Definition: attr.h:179
Annotation for parent scope.
Definition: attr.h:27
Operator implementation generator.
Definition: attr.h:118
#define PYBIND11_NAMESPACE
Definition: detail/common.h:26
PyObject * ptr() const
Return the underlying PyObject * pointer.
Definition: pytypes.h:182
std::size_t size_t
return_value_policy policy
Return value policy associated with this function.
Definition: attr.h:161
constexpr bool expected_num_args(size_t nargs, bool has_args, bool has_kwargs)
Check the number of named arguments at compile time.
Definition: attr.h:488
Tag for a new-style __init__ defined in detail/init.h
Definition: attr.h:292
bool is_constructor
True if name == &#39;init&#39;.
Definition: attr.h:164
handle sibling
Python handle to the sibling function representing an overload chain.
Definition: attr.h:194
typename exactly_one< Predicate, Default, Ts... >::type exactly_one_t
bool flag_noconvert
If set, do not allow conversion (requires a supporting type caster!)
Definition: cast.h:1793
static void init(const multiple_inheritance &, type_record *r)
Definition: attr.h:411
const char * name
If non-null, this is a named kwargs argument.
Definition: cast.h:1792
static void init(const Args &... args, function_record *r)
Definition: attr.h:459
std::is_base_of< pyobject_tag, remove_reference_t< T > > is_pyobject
Definition: pytypes.h:47
std::string type
The C++ type name of the default value (only available when compiled in debug mode) ...
Definition: cast.h:1836
is_method(const handle &c)
Definition: attr.h:21
Internal data structure which holds metadata about a bound function (signature, overloads, etc.)
Definition: attr.h:134
Internal data associated with a single function call.
Definition: cast.h:1859
static void init(const doc &n, function_record *r)
Definition: attr.h:317
bool is_stateless
True if this is a stateless function pointer.
Definition: attr.h:170
test_initializer class_("class_", test_submodule_class_)
Definition: pybind11.h:888
const char * name
Argument name.
Definition: attr.h:123
arr data(const arr &a, Ix... index)
Annotation which enables dynamic attributes, i.e. adds __dict__ to a class.
Definition: attr.h:51
#define PYBIND11_NOINLINE
Definition: detail/common.h:86
The &#39;instance&#39; type which needs to be standard layout (need to be able to use &#39;offsetof&#39;) ...
handle value
Definition: attr.h:36
static void init(const base< T > &, type_record *r)
Definition: attr.h:405
static void init(const is_method &s, function_record *r)
Definition: attr.h:339
Internal data structure which holds metadata about a keyword argument.
Definition: attr.h:122
Recursively iterate over variadic template arguments.
Definition: attr.h:458
const bool value
Definition: attr.h:68
size_t function_call handle ret
Definition: pybind11.h:1610
static void postcall(function_call &call, handle ret)
Definition: attr.h:454
handle scope
Python handle to the parent scope (a class or a module)
Definition: attr.h:191
static void init(const arg &a, function_record *r)
Definition: attr.h:358
bool none
True if None is allowed when loading.
Definition: attr.h:127
Annotation which requests that a special metaclass is created for a type.
Definition: attr.h:57
handle metaclass
Custom metaclass (optional)
Definition: attr.h:240
handle scope
Handle to the parent scope.
Definition: attr.h:207
detail::initimpl::constructor< Args... > init()
Binds an existing constructor taking arguments Args...
Definition: pybind11.h:1371
static void init(const buffer_protocol &, type_record *r)
Definition: attr.h:421
#define NAMESPACE_END(name)
Definition: detail/common.h:16
const char * descr
The (optional) description of the default value.
Definition: cast.h:1833
argument_record(const char *name, const char *descr, handle value, bool convert, bool none)
Definition: attr.h:129
static void init(const module_local &l, type_record *r)
Definition: attr.h:431
static void init(const T &, function_record *)
Default implementation: do nothing.
Definition: attr.h:304
const char * value
Definition: attr.h:30
typename exactly_one_t< is_call_guard, call_guard<>, Extra... >::type extract_guard_t
Extract the type from the first call_guard in Extras... (or void_type if none found) ...
Definition: attr.h:482
bool module_local
Is the class definition local to the module shared object?
Definition: attr.h:255
static void init(const char *d, type_record *r)
Definition: attr.h:323
return_value_policy
Approach used to cast a previously unknown C++ instance into a Python object.
Annotation indicating that a function is an overload associated with a given "sibling".
Definition: attr.h:36
object value
The default value.
Definition: cast.h:1831
bool multiple_inheritance
Multiple inheritance marker.
Definition: attr.h:243
bool is_method
True if this is a method.
Definition: attr.h:182
Process an attribute specifying the function&#39;s docstring (provided as a C-style string) ...
Definition: attr.h:321
bool buffer_protocol
Does the class implement the buffer protocol?
Definition: attr.h:249
size_t function_call & call
Definition: pybind11.h:1610
static void init(const sibling &s, function_record *r)
Definition: attr.h:334
Annotation for operators.
Definition: attr.h:24
Annotation to mark enums as an arithmetic type.
Definition: attr.h:71
char * name
Function name.
Definition: attr.h:140
handle value
Definition: attr.h:58
constexpr size_t constexpr_sum()
Compile-time integer sum.
Keep patient alive while nurse lives.
Definition: attr.h:45
static void precall(function_call &call)
Definition: attr.h:467
static void precall(function_call &)
Definition: attr.h:306
bool default_holder
Is the default (unique_ptr) holder type used?
Definition: attr.h:252
bool dynamic_attr
Does the class manage a dict?
Definition: attr.h:246
def d(s)
Definition: mkdoc.py:69
static void init(const char *d, function_record *r)
Definition: attr.h:322
int nargs
Definition: benchmark.py:7
Annotation for documentation.
Definition: attr.h:30
op_id
Enumeration with all supported operator types.
Definition: operators.h:25
Annotation which enables the buffer protocol for a type.
Definition: attr.h:54
static void postcall(function_call &call, handle fn_ret)
Definition: attr.h:471
def doc()
Definition: conftest.py:152
static void init(const scope &s, function_record *r)
Definition: attr.h:344
static void init(const arg_v &a, function_record *r)
Definition: attr.h:367
static void init(const T &, type_record *)
Definition: attr.h:305
Annotation indicating that a class derives from another given type.
Definition: attr.h:39
const detail::type_info * type
Definition: cast.h:453
Annotation for function names.
Definition: attr.h:33
std::vector< bool > args_convert
The convert value the arguments should be loaded with.
Definition: cast.h:1869
Helper type to replace &#39;void&#39; in some expressions.
return os str()
metaclass(handle value)
Override pybind11&#39;s default metaclass.
Definition: attr.h:64
static void init(const return_value_policy &p, function_record *r)
Definition: attr.h:329
void ignore_unused(const int *)
Ignore that a variable is unused in compiler warnings.
#define PYBIND11_DEPRECATED(reason)
Definition: detail/common.h:92
static void init(const metaclass &m, type_record *r)
Definition: attr.h:426
void keep_alive_impl(size_t Nurse, size_t Patient, function_call &call, handle ret)
handle value
Definition: attr.h:27
bool convert
True if the argument is allowed to convert when loading.
Definition: attr.h:126
#define NAMESPACE_BEGIN(name)
Definition: detail/common.h:13
const char * doc
Optional docstring.
Definition: attr.h:237
bool is_new_style_constructor
True if this is a new-style __init__ defined in detail/init.h
Definition: attr.h:167
std::vector< argument_record > args
List of registered keyword arguments.
Definition: attr.h:149
handle class_
Definition: attr.h:21
handle value
Associated Python object.
Definition: attr.h:125
static void init(const Args &... args, type_record *r)
Definition: attr.h:463
Special data structure which (temporarily) holds metadata about a bound class.
Definition: attr.h:201
list bases
List of base classes of the newly created type.
Definition: attr.h:234
static void init(const is_operator &, function_record *r)
Definition: attr.h:349
bool flag_none
If set (the default), allow None to be passed to this argument.
Definition: cast.h:1794
typename std::enable_if< B, T >::type enable_if_t
from cpp_future import (convenient aliases from C++14/17)
const handle & inc_ref() const &
Definition: pytypes.h:190
const char * value
Definition: attr.h:33
bool is_operator
True if this is an operator (add), etc.
Definition: attr.h:173
Annotation that marks a class as local to the module:
Definition: attr.h:68
const char * descr
Human-readable version of the argument value.
Definition: attr.h:124
bool has_args
True if the function has a &#39;*args&#39; argument.
Definition: attr.h:176
Annotation indicating that a class is involved in a multiple inheritance relationship.
Definition: attr.h:48
static void postcall(function_call &, handle)
Definition: attr.h:307