11 #if PY_VERSION_HEX >= 0x03040000 12 #define _COLLECTIONS_ABC "_collections_abc" 13 #elif PY_VERSION_HEX >= 0x03030000 14 #define _COLLECTIONS_ABC "collections.abc" 16 #define _COLLECTIONS_ABC "_abcoll" 19 static void _register_collection(PyTypeObject *type,
const char *abc) {
20 PyObject *sys_modules = PyImport_GetModuleDict();
21 if (sys_modules !=
nullptr) {
22 PyObject *module = PyDict_GetItemString(sys_modules, _COLLECTIONS_ABC);
23 if (module !=
nullptr) {
24 PyObject *dict = PyModule_GetDict(module);
25 if (module !=
nullptr) {
26 #if PY_MAJOR_VERSION >= 3 27 static PyObject *register_str = PyUnicode_InternFromString(
"register");
29 static PyObject *register_str = PyString_InternFromString(
"register");
31 PyObject *sequence = PyDict_GetItemString(dict, abc);
32 if (sequence !=
nullptr) {
33 if (PyObject_CallMethodObjArgs(sequence, register_str, (PyObject *)type,
nullptr) ==
nullptr) {
46 static void Dtool_WrapperBase_dealloc(PyObject *
self) {
47 Dtool_WrapperBase *wrap = (Dtool_WrapperBase *)
self;
49 Py_XDECREF(wrap->_self);
50 Py_TYPE(
self)->tp_free(
self);
53 static PyObject *Dtool_WrapperBase_repr(PyObject *
self) {
54 Dtool_WrapperBase *wrap = (Dtool_WrapperBase *)
self;
55 nassertr(wrap,
nullptr);
57 PyObject *repr = PyObject_Repr(wrap->_self);
59 #if PY_MAJOR_VERSION >= 3 60 result = PyUnicode_FromFormat(
"<%s[] of %s>", wrap->_name, PyUnicode_AsUTF8(repr));
62 result = PyString_FromFormat(
"<%s[] of %s>", wrap->_name, PyString_AS_STRING(repr));
68 static PyObject *Dtool_SequenceWrapper_repr(PyObject *
self) {
69 Dtool_SequenceWrapper *wrap = (Dtool_SequenceWrapper *)
self;
70 nassertr(wrap,
nullptr);
73 if (wrap->_len_func !=
nullptr) {
74 len = wrap->_len_func(wrap->_base._self);
78 PyErr_Restore(
nullptr,
nullptr,
nullptr);
79 return Dtool_WrapperBase_repr(
self);
82 PyObject *repr = PyObject_Repr(wrap->_base._self);
84 #if PY_MAJOR_VERSION >= 3 85 result = PyUnicode_FromFormat(
"<%s[%zd] of %s>", wrap->_base._name, len, PyUnicode_AsUTF8(repr));
87 result = PyString_FromFormat(
"<%s[%zd] of %s>", wrap->_base._name, len, PyString_AS_STRING(repr));
93 static Py_ssize_t Dtool_SequenceWrapper_length(PyObject *
self) {
94 Dtool_SequenceWrapper *wrap = (Dtool_SequenceWrapper *)
self;
96 if (wrap->_len_func !=
nullptr) {
97 return wrap->_len_func(wrap->_base._self);
99 Dtool_Raise_TypeError(
"property does not support len()");
104 static PyObject *Dtool_SequenceWrapper_getitem(PyObject *
self, Py_ssize_t index) {
105 Dtool_SequenceWrapper *wrap = (Dtool_SequenceWrapper *)
self;
106 nassertr(wrap,
nullptr);
107 nassertr(wrap->_getitem_func,
nullptr);
108 return wrap->_getitem_func(wrap->_base._self, index);
114 static int Dtool_SequenceWrapper_contains(PyObject *
self, PyObject *value) {
115 Dtool_SequenceWrapper *wrap = (Dtool_SequenceWrapper *)
self;
117 nassertr(wrap->_len_func, -1);
118 nassertr(wrap->_getitem_func, -1);
120 Py_ssize_t length = wrap->_len_func(wrap->_base._self);
124 for (Py_ssize_t index = 0; index < length; ++index) {
125 PyObject *item = wrap->_getitem_func(wrap->_base._self, index);
126 if (item !=
nullptr) {
127 int cmp = PyObject_RichCompareBool(item, value, Py_EQ);
145 static PyObject *Dtool_SequenceWrapper_index(PyObject *
self, PyObject *value) {
146 Dtool_SequenceWrapper *wrap = (Dtool_SequenceWrapper *)
self;
147 nassertr(wrap,
nullptr);
148 nassertr(wrap->_len_func,
nullptr);
149 nassertr(wrap->_getitem_func,
nullptr);
151 Py_ssize_t length = wrap->_len_func(wrap->_base._self);
155 for (Py_ssize_t index = 0; index < length; ++index) {
156 PyObject *item = wrap->_getitem_func(wrap->_base._self, index);
157 if (item !=
nullptr) {
158 int cmp = PyObject_RichCompareBool(item, value, Py_EQ);
170 return PyErr_Format(PyExc_ValueError,
"%s.index() did not find value", wrap->_base._name);
177 static PyObject *Dtool_SequenceWrapper_count(PyObject *
self, PyObject *value) {
178 Dtool_SequenceWrapper *wrap = (Dtool_SequenceWrapper *)
self;
179 nassertr(wrap,
nullptr);
180 Py_ssize_t index = 0;
181 if (wrap->_len_func !=
nullptr) {
182 index = wrap->_len_func(wrap->_base._self);
184 return Dtool_Raise_TypeError(
"property does not support count()");
188 nassertr(wrap->_getitem_func,
nullptr);
191 PyObject *item = wrap->_getitem_func(wrap->_base._self, index);
192 if (item ==
nullptr) {
195 int cmp = PyObject_RichCompareBool(item, value, Py_EQ);
203 #if PY_MAJOR_VERSION >= 3 204 return PyLong_FromLong(count);
206 return PyInt_FromLong(count);
213 static int Dtool_MutableSequenceWrapper_setitem(PyObject *
self, Py_ssize_t index, PyObject *value) {
214 Dtool_MutableSequenceWrapper *wrap = (Dtool_MutableSequenceWrapper *)
self;
216 if (wrap->_setitem_func !=
nullptr) {
217 return wrap->_setitem_func(wrap->_base._self, index, value);
219 Dtool_Raise_TypeError(
"property does not support item assignment");
228 static PyObject *Dtool_MutableSequenceWrapper_clear(PyObject *
self, PyObject *) {
229 Dtool_MutableSequenceWrapper *wrap = (Dtool_MutableSequenceWrapper *)
self;
230 nassertr(wrap,
nullptr);
231 Py_ssize_t index = 0;
232 if (wrap->_len_func !=
nullptr && wrap->_setitem_func !=
nullptr) {
233 index = wrap->_len_func(wrap->_base._self);
235 return Dtool_Raise_TypeError(
"property does not support clear()");
242 if (wrap->_setitem_func(wrap->_base._self, index,
nullptr) != 0) {
254 static PyObject *Dtool_MutableSequenceWrapper_remove(PyObject *
self, PyObject *value) {
255 Dtool_MutableSequenceWrapper *wrap = (Dtool_MutableSequenceWrapper *)
self;
256 nassertr(wrap,
nullptr);
257 Py_ssize_t length = 0;
258 if (wrap->_len_func !=
nullptr && wrap->_setitem_func !=
nullptr) {
259 length = wrap->_len_func(wrap->_base._self);
261 return Dtool_Raise_TypeError(
"property does not support remove()");
266 nassertr(wrap->_getitem_func,
nullptr);
267 for (Py_ssize_t index = 0; index < length; ++index) {
268 PyObject *item = wrap->_getitem_func(wrap->_base._self, index);
269 if (item !=
nullptr) {
270 int cmp = PyObject_RichCompareBool(item, value, Py_EQ);
272 if (wrap->_setitem_func(wrap->_base._self, index,
nullptr) == 0) {
287 return PyErr_Format(PyExc_ValueError,
"%s.remove() did not find value", wrap->_base._name);
295 static PyObject *Dtool_MutableSequenceWrapper_pop(PyObject *
self, PyObject *args) {
296 Dtool_MutableSequenceWrapper *wrap = (Dtool_MutableSequenceWrapper *)
self;
297 nassertr(wrap,
nullptr);
298 if (wrap->_getitem_func ==
nullptr || wrap->_setitem_func ==
nullptr ||
299 wrap->_len_func ==
nullptr) {
300 return Dtool_Raise_TypeError(
"property does not support pop()");
303 Py_ssize_t length = wrap->_len_func(wrap->_base._self);
305 switch (PyTuple_GET_SIZE(args)) {
310 index = PyNumber_AsSsize_t(PyTuple_GET_ITEM(args, 0), PyExc_IndexError);
311 if (index == -1 && _PyErr_OCCURRED()) {
319 return Dtool_Raise_TypeError(
"pop([i=-1]) takes 0 or 1 arguments");
323 return PyErr_Format(PyExc_IndexError,
"%s.pop() from empty sequence", wrap->_base._name);
327 PyObject *value = wrap->_getitem_func(wrap->_base._self, index);
328 if (value !=
nullptr) {
329 if (wrap->_setitem_func(wrap->_base._self, index,
nullptr) != 0) {
341 static PyObject *Dtool_MutableSequenceWrapper_append(PyObject *
self, PyObject *arg) {
342 Dtool_MutableSequenceWrapper *wrap = (Dtool_MutableSequenceWrapper *)
self;
343 nassertr(wrap,
nullptr);
344 if (wrap->_insert_func ==
nullptr) {
345 return Dtool_Raise_TypeError(
"property does not support append()");
347 return wrap->_insert_func(wrap->_base._self, (
size_t)-1, arg);
354 static PyObject *Dtool_MutableSequenceWrapper_insert(PyObject *
self, PyObject *args) {
355 Dtool_MutableSequenceWrapper *wrap = (Dtool_MutableSequenceWrapper *)
self;
356 nassertr(wrap,
nullptr);
357 if (wrap->_insert_func ==
nullptr) {
358 return Dtool_Raise_TypeError(
"property does not support insert()");
360 if (PyTuple_GET_SIZE(args) != 2) {
361 return Dtool_Raise_TypeError(
"insert() takes exactly 2 arguments");
363 Py_ssize_t index = PyNumber_AsSsize_t(PyTuple_GET_ITEM(args, 0), PyExc_IndexError);
364 if (index == -1 && _PyErr_OCCURRED()) {
368 if (wrap->_len_func !=
nullptr) {
369 index += wrap->_len_func(wrap->_base._self);
371 return PyErr_Format(PyExc_TypeError,
"%s.insert() does not support negative indices", wrap->_base._name);
374 return wrap->_insert_func(wrap->_base._self, (ssize_t)std::max(index, (Py_ssize_t)0), PyTuple_GET_ITEM(args, 1));
384 static PyObject *Dtool_MutableSequenceWrapper_extend(PyObject *
self, PyObject *arg) {
385 Dtool_MutableSequenceWrapper *wrap = (Dtool_MutableSequenceWrapper *)
self;
386 nassertr(wrap,
nullptr);
387 if (wrap->_insert_func ==
nullptr) {
388 return Dtool_Raise_TypeError(
"property does not support extend()");
390 PyObject *iter = PyObject_GetIter(arg);
391 if (iter ==
nullptr) {
394 PyObject *next = PyIter_Next(iter);
395 PyObject *retval =
nullptr;
396 while (next !=
nullptr) {
397 retval = wrap->_insert_func(wrap->_base._self, (
size_t)-1, next);
399 if (retval ==
nullptr) {
404 next = PyIter_Next(iter);
415 static int Dtool_MappingWrapper_contains(PyObject *
self, PyObject *key) {
416 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
418 nassertr(wrap->_getitem_func, -1);
419 PyObject *value = wrap->_getitem_func(wrap->_base._self, key);
420 if (value !=
nullptr) {
423 }
else if (_PyErr_OCCURRED() == PyExc_KeyError ||
424 _PyErr_OCCURRED() == PyExc_TypeError) {
425 PyErr_Restore(
nullptr,
nullptr,
nullptr);
432 static PyObject *Dtool_MappingWrapper_getitem(PyObject *
self, PyObject *key) {
433 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
434 nassertr(wrap,
nullptr);
435 nassertr(wrap->_getitem_func,
nullptr);
436 return wrap->_getitem_func(wrap->_base._self, key);
443 static PyObject *Dtool_MappingWrapper_iter(PyObject *
self) {
444 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
445 nassertr(wrap,
nullptr);
447 if (wrap->_keys._len_func ==
nullptr || wrap->_keys._getitem_func ==
nullptr) {
448 return PyErr_Format(PyExc_TypeError,
"%s is not iterable", wrap->_base._name);
451 Dtool_SequenceWrapper *keys = Dtool_NewSequenceWrapper(wrap->_base._self, wrap->_base._name);
452 if (keys !=
nullptr) {
453 keys->_len_func = wrap->_keys._len_func;
454 keys->_getitem_func = wrap->_keys._getitem_func;
455 return PySeqIter_New((PyObject *)keys);
466 static PyObject *Dtool_MappingWrapper_get(PyObject *
self, PyObject *args) {
467 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
468 nassertr(wrap,
nullptr);
469 nassertr(wrap->_getitem_func,
nullptr);
470 Py_ssize_t size = PyTuple_GET_SIZE(args);
471 if (size != 1 && size != 2) {
472 return PyErr_Format(PyExc_TypeError,
"%s.get() takes 1 or 2 arguments", wrap->_base._name);
474 PyObject *defvalue = Py_None;
476 defvalue = PyTuple_GET_ITEM(args, 1);
478 PyObject *key = PyTuple_GET_ITEM(args, 0);
479 PyObject *value = wrap->_getitem_func(wrap->_base._self, key);
480 if (value !=
nullptr) {
482 }
else if (_PyErr_OCCURRED() == PyExc_KeyError) {
483 PyErr_Restore(
nullptr,
nullptr,
nullptr);
494 static PyObject *Dtool_MappingWrapper_Keys_repr(PyObject *
self) {
495 Dtool_WrapperBase *wrap = (Dtool_WrapperBase *)
self;
496 nassertr(wrap,
nullptr);
498 PyObject *repr = PyObject_Repr(wrap->_self);
500 #if PY_MAJOR_VERSION >= 3 501 result = PyUnicode_FromFormat(
"<%s.keys() of %s>", wrap->_name, PyUnicode_AsUTF8(repr));
503 result = PyString_FromFormat(
"<%s.keys() of %s>", wrap->_name, PyString_AS_STRING(repr));
512 static PyObject *Dtool_MappingWrapper_keys(PyObject *
self, PyObject *) {
513 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
514 nassertr(wrap,
nullptr);
516 if (wrap->_keys._len_func ==
nullptr || wrap->_keys._getitem_func ==
nullptr) {
517 return Dtool_Raise_TypeError(
"property does not support keys()");
520 Dtool_MappingWrapper *keys = (Dtool_MappingWrapper *)PyObject_MALLOC(
sizeof(Dtool_MappingWrapper));
521 if (keys ==
nullptr) {
522 return PyErr_NoMemory();
525 static PySequenceMethods seq_methods = {
526 Dtool_SequenceWrapper_length,
529 Dtool_SequenceWrapper_getitem,
533 Dtool_SequenceWrapper_contains,
538 static PyTypeObject wrapper_type = {
539 PyVarObject_HEAD_INIT(
nullptr, 0)
541 sizeof(Dtool_SequenceWrapper),
543 Dtool_WrapperBase_dealloc,
548 Dtool_MappingWrapper_Keys_repr,
555 PyObject_GenericGetAttr,
556 PyObject_GenericSetAttr,
558 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_CHECKTYPES,
587 static bool registered =
false;
591 if (PyType_Ready(&wrapper_type) < 0) {
596 _register_collection((PyTypeObject *)&wrapper_type,
"MappingView");
599 (void)PyObject_INIT(keys, &wrapper_type);
600 Py_XINCREF(wrap->_base._self);
601 keys->_base._self = wrap->_base._self;
602 keys->_base._name = wrap->_base._name;
603 keys->_keys._len_func = wrap->_keys._len_func;
604 keys->_keys._getitem_func = wrap->_keys._getitem_func;
605 keys->_getitem_func = wrap->_getitem_func;
606 keys->_setitem_func =
nullptr;
607 return (PyObject *)keys;
613 static PyObject *Dtool_MappingWrapper_Values_repr(PyObject *
self) {
614 Dtool_WrapperBase *wrap = (Dtool_WrapperBase *)
self;
615 nassertr(wrap,
nullptr);
617 PyObject *repr = PyObject_Repr(wrap->_self);
619 #if PY_MAJOR_VERSION >= 3 620 result = PyUnicode_FromFormat(
"<%s.values() of %s>", wrap->_name, PyUnicode_AsUTF8(repr));
622 result = PyString_FromFormat(
"<%s.values() of %s>", wrap->_name, PyString_AS_STRING(repr));
628 static PyObject *Dtool_MappingWrapper_Values_getitem(PyObject *
self, Py_ssize_t index) {
629 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
630 nassertr(wrap,
nullptr);
631 nassertr(wrap->_keys._getitem_func,
nullptr);
633 PyObject *key = wrap->_keys._getitem_func(wrap->_base._self, index);
634 if (key !=
nullptr) {
635 PyObject *value = wrap->_getitem_func(wrap->_base._self, key);
645 static PyObject *Dtool_MappingWrapper_values(PyObject *
self, PyObject *) {
646 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
647 nassertr(wrap,
nullptr);
648 nassertr(wrap->_getitem_func,
nullptr);
650 if (wrap->_keys._len_func ==
nullptr || wrap->_keys._getitem_func ==
nullptr) {
651 return Dtool_Raise_TypeError(
"property does not support values()");
654 Dtool_MappingWrapper *values = (Dtool_MappingWrapper *)PyObject_MALLOC(
sizeof(Dtool_MappingWrapper));
655 if (values ==
nullptr) {
656 return PyErr_NoMemory();
659 static PySequenceMethods seq_methods = {
660 Dtool_SequenceWrapper_length,
663 Dtool_MappingWrapper_Values_getitem,
667 Dtool_MappingWrapper_contains,
672 static PyTypeObject wrapper_type = {
673 PyVarObject_HEAD_INIT(
nullptr, 0)
675 sizeof(Dtool_MappingWrapper),
677 Dtool_WrapperBase_dealloc,
682 Dtool_MappingWrapper_Values_repr,
689 PyObject_GenericGetAttr,
690 PyObject_GenericSetAttr,
692 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_CHECKTYPES,
721 static bool registered =
false;
725 if (PyType_Ready(&wrapper_type) < 0) {
730 _register_collection((PyTypeObject *)&wrapper_type,
"ValuesView");
733 (void)PyObject_INIT(values, &wrapper_type);
734 Py_XINCREF(wrap->_base._self);
735 values->_base._self = wrap->_base._self;
736 values->_base._name = wrap->_base._name;
737 values->_keys._len_func = wrap->_keys._len_func;
738 values->_keys._getitem_func = wrap->_keys._getitem_func;
739 values->_getitem_func = wrap->_getitem_func;
740 values->_setitem_func =
nullptr;
741 return (PyObject *)values;
747 static PyObject *Dtool_MappingWrapper_Items_repr(PyObject *
self) {
748 Dtool_WrapperBase *wrap = (Dtool_WrapperBase *)
self;
749 nassertr(wrap,
nullptr);
751 PyObject *repr = PyObject_Repr(wrap->_self);
753 #if PY_MAJOR_VERSION >= 3 754 result = PyUnicode_FromFormat(
"<%s.items() of %s>", wrap->_name, PyUnicode_AsUTF8(repr));
756 result = PyString_FromFormat(
"<%s.items() of %s>", wrap->_name, PyString_AS_STRING(repr));
762 static PyObject *Dtool_MappingWrapper_Items_getitem(PyObject *
self, Py_ssize_t index) {
763 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
764 nassertr(wrap,
nullptr);
765 nassertr(wrap->_keys._getitem_func,
nullptr);
767 PyObject *key = wrap->_keys._getitem_func(wrap->_base._self, index);
768 if (key !=
nullptr) {
769 PyObject *value = wrap->_getitem_func(wrap->_base._self, key);
770 if (value !=
nullptr) {
772 PyObject *item = PyTuple_New(2);
773 PyTuple_SET_ITEM(item, 0, key);
774 PyTuple_SET_ITEM(item, 1, value);
787 static PyObject *Dtool_MappingWrapper_items(PyObject *
self, PyObject *) {
788 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
789 nassertr(wrap,
nullptr);
790 nassertr(wrap->_getitem_func,
nullptr);
792 if (wrap->_keys._len_func ==
nullptr || wrap->_keys._getitem_func ==
nullptr) {
793 return Dtool_Raise_TypeError(
"property does not support items()");
796 Dtool_MappingWrapper *items = (Dtool_MappingWrapper *)PyObject_MALLOC(
sizeof(Dtool_MappingWrapper));
797 if (items ==
nullptr) {
798 return PyErr_NoMemory();
801 static PySequenceMethods seq_methods = {
802 Dtool_SequenceWrapper_length,
805 Dtool_MappingWrapper_Items_getitem,
809 Dtool_MappingWrapper_contains,
814 static PyTypeObject wrapper_type = {
815 PyVarObject_HEAD_INIT(
nullptr, 0)
817 sizeof(Dtool_MappingWrapper),
819 Dtool_WrapperBase_dealloc,
824 Dtool_MappingWrapper_Items_repr,
831 PyObject_GenericGetAttr,
832 PyObject_GenericSetAttr,
834 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_CHECKTYPES,
863 static bool registered =
false;
867 if (PyType_Ready(&wrapper_type) < 0) {
872 _register_collection((PyTypeObject *)&wrapper_type,
"MappingView");
875 (void)PyObject_INIT(items, &wrapper_type);
876 Py_XINCREF(wrap->_base._self);
877 items->_base._self = wrap->_base._self;
878 items->_base._name = wrap->_base._name;
879 items->_keys._len_func = wrap->_keys._len_func;
880 items->_keys._getitem_func = wrap->_keys._getitem_func;
881 items->_getitem_func = wrap->_getitem_func;
882 items->_setitem_func =
nullptr;
883 return (PyObject *)items;
889 static int Dtool_MutableMappingWrapper_setitem(PyObject *
self, PyObject *key, PyObject *value) {
890 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
891 nassertr(wrap->_setitem_func !=
nullptr, -1);
892 return wrap->_setitem_func(wrap->_base._self, key, value);
899 static PyObject *Dtool_MutableMappingWrapper_pop(PyObject *
self, PyObject *args) {
900 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
901 nassertr(wrap,
nullptr);
902 if (wrap->_getitem_func ==
nullptr || wrap->_setitem_func ==
nullptr) {
903 return Dtool_Raise_TypeError(
"property does not support pop()");
906 Py_ssize_t size = PyTuple_GET_SIZE(args);
907 if (size != 1 && size != 2) {
908 return PyErr_Format(PyExc_TypeError,
"%s.pop() takes 1 or 2 arguments", wrap->_base._name);
910 PyObject *defvalue = Py_None;
912 defvalue = PyTuple_GET_ITEM(args, 1);
915 PyObject *key = PyTuple_GET_ITEM(args, 0);
916 PyObject *value = wrap->_getitem_func(wrap->_base._self, key);
917 if (value !=
nullptr) {
919 if (wrap->_setitem_func(wrap->_base._self, key,
nullptr) == 0) {
925 }
else if (_PyErr_OCCURRED() == PyExc_KeyError) {
926 PyErr_Restore(
nullptr,
nullptr,
nullptr);
938 static PyObject *Dtool_MutableMappingWrapper_popitem(PyObject *
self, PyObject *) {
939 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
940 nassertr(wrap,
nullptr);
941 if (wrap->_getitem_func ==
nullptr || wrap->_setitem_func ==
nullptr ||
942 wrap->_keys._len_func ==
nullptr || wrap->_keys._getitem_func ==
nullptr) {
943 return Dtool_Raise_TypeError(
"property does not support popitem()");
946 Py_ssize_t length = wrap->_keys._len_func(wrap->_base._self);
948 return PyErr_Format(PyExc_KeyError,
"%s is empty", wrap->_base._name);
951 PyObject *key = wrap->_keys._getitem_func(wrap->_base._self, length - 1);
952 if (key !=
nullptr) {
953 PyObject *value = wrap->_getitem_func(wrap->_base._self, key);
954 if (value !=
nullptr) {
956 if (wrap->_setitem_func(wrap->_base._self, key,
nullptr) == 0) {
957 PyObject *item = PyTuple_New(2);
958 PyTuple_SET_ITEM(item, 0, key);
959 PyTuple_SET_ITEM(item, 1, value);
972 static PyObject *Dtool_MutableMappingWrapper_clear(PyObject *
self, PyObject *) {
973 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
974 nassertr(wrap,
nullptr);
975 Py_ssize_t index = 0;
976 if (wrap->_keys._len_func !=
nullptr && wrap->_keys._getitem_func !=
nullptr &&
977 wrap->_setitem_func !=
nullptr) {
978 index = wrap->_keys._len_func(wrap->_base._self);
980 return Dtool_Raise_TypeError(
"property does not support clear()");
987 PyObject *key = wrap->_keys._getitem_func(wrap->_base._self, index);
988 if (key !=
nullptr) {
989 int result = wrap->_setitem_func(wrap->_base._self, key,
nullptr);
1005 static PyObject *Dtool_MutableMappingWrapper_setdefault(PyObject *
self, PyObject *args) {
1006 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
1007 nassertr(wrap,
nullptr);
1009 if (wrap->_getitem_func ==
nullptr || wrap->_setitem_func ==
nullptr) {
1010 return Dtool_Raise_TypeError(
"property does not support setdefault()");
1013 Py_ssize_t size = PyTuple_GET_SIZE(args);
1014 if (size != 1 && size != 2) {
1015 return PyErr_Format(PyExc_TypeError,
"%s.setdefault() takes 1 or 2 arguments", wrap->_base._name);
1017 PyObject *defvalue = Py_None;
1019 defvalue = PyTuple_GET_ITEM(args, 1);
1021 PyObject *key = PyTuple_GET_ITEM(args, 0);
1022 PyObject *value = wrap->_getitem_func(wrap->_base._self, key);
1023 if (value !=
nullptr) {
1025 }
else if (_PyErr_OCCURRED() == PyExc_KeyError) {
1026 PyErr_Restore(
nullptr,
nullptr,
nullptr);
1027 if (wrap->_setitem_func(wrap->_base._self, key, defvalue) == 0) {
1028 Py_INCREF(defvalue);
1039 static PyObject *Dtool_MutableMappingWrapper_update(PyObject *
self, PyObject *args, PyObject *kwargs) {
1040 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)
self;
1041 nassertr(wrap,
nullptr);
1043 if (wrap->_getitem_func ==
nullptr || wrap->_setitem_func ==
nullptr) {
1044 return Dtool_Raise_TypeError(
"property does not support update()");
1049 switch (PyTuple_GET_SIZE(args)) {
1051 if (kwargs ==
nullptr) {
1059 if (PyDict_Check(PyTuple_GET_ITEM(args, 0)) && (kwargs ==
nullptr || Py_SIZE(kwargs) == 0)) {
1060 dict = PyTuple_GET_ITEM(args, 0);
1065 return PyErr_Format(PyExc_TypeError,
"%s.update() takes either a dict argument or keyword arguments", wrap->_base._name);
1068 PyObject *key, *value;
1070 while (PyDict_Next(dict, &pos, &key, &value)) {
1071 if (wrap->_setitem_func(wrap->_base._self, key, value) != 0) {
1082 static PyObject *Dtool_GeneratorWrapper_iternext(PyObject *
self) {
1083 Dtool_GeneratorWrapper *wrap = (Dtool_GeneratorWrapper *)
self;
1084 nassertr(wrap,
nullptr);
1085 nassertr(wrap->_iternext_func,
nullptr);
1086 return wrap->_iternext_func(wrap->_base._self);
1094 Dtool_StaticProperty_dealloc(PyDescrObject *descr) {
1095 #if PY_VERSION_HEX >= 0x03080000 1096 PyObject_GC_UnTrack(descr);
1098 _PyObject_GC_UNTRACK(descr);
1100 Py_XDECREF(descr->d_type);
1101 Py_XDECREF(descr->d_name);
1105 PyObject_GC_Del(descr);
1109 Dtool_StaticProperty_repr(PyDescrObject *descr,
const char *format) {
1110 #if PY_MAJOR_VERSION >= 3 1111 return PyUnicode_FromFormat(
"<attribute '%s' of '%s'>",
1112 PyUnicode_AsUTF8(descr->d_name),
1113 descr->d_type->tp_name);
1115 return PyString_FromFormat(
"<attribute '%s' of '%s'>",
1116 PyString_AS_STRING(descr->d_name),
1117 descr->d_type->tp_name);
1122 Dtool_StaticProperty_traverse(PyObject *
self, visitproc visit,
void *arg) {
1123 PyDescrObject *descr = (PyDescrObject *)
self;
1124 Py_VISIT(descr->d_type);
1129 Dtool_StaticProperty_get(PyGetSetDescrObject *descr, PyObject *obj, PyObject *type) {
1130 if (descr->d_getset->get !=
nullptr) {
1131 return descr->d_getset->get(obj, descr->d_getset->closure);
1133 return PyErr_Format(PyExc_AttributeError,
1134 "attribute '%s' of type '%.100s' is not readable",
1135 #
if PY_MAJOR_VERSION >= 3
1136 PyUnicode_AsUTF8(((PyDescrObject *)descr)->d_name),
1138 PyString_AS_STRING(((PyDescrObject *)descr)->d_name),
1140 ((PyDescrObject *)descr)->d_type->tp_name);
1145 Dtool_StaticProperty_set(PyGetSetDescrObject *descr, PyObject *obj, PyObject *value) {
1146 if (descr->d_getset->set !=
nullptr) {
1147 return descr->d_getset->set(obj, value, descr->d_getset->closure);
1149 PyErr_Format(PyExc_AttributeError,
1150 "attribute '%s' of type '%.100s' is not writable",
1151 #
if PY_MAJOR_VERSION >= 3
1152 PyUnicode_AsUTF8(((PyDescrObject *)descr)->d_name),
1154 PyString_AS_STRING(((PyDescrObject *)descr)->d_name),
1156 ((PyDescrObject *)descr)->d_type->tp_name);
1164 Dtool_SequenceWrapper *Dtool_NewSequenceWrapper(PyObject *
self,
const char *name) {
1165 Dtool_SequenceWrapper *wrap = (Dtool_SequenceWrapper *)PyObject_MALLOC(
sizeof(Dtool_SequenceWrapper));
1166 if (wrap ==
nullptr) {
1167 return (Dtool_SequenceWrapper *)PyErr_NoMemory();
1170 static PySequenceMethods seq_methods = {
1171 Dtool_SequenceWrapper_length,
1174 Dtool_SequenceWrapper_getitem,
1178 Dtool_SequenceWrapper_contains,
1183 static PyMethodDef methods[] = {
1184 {
"index", &Dtool_SequenceWrapper_index, METH_O,
nullptr},
1185 {
"count", &Dtool_SequenceWrapper_count, METH_O,
nullptr},
1186 {
nullptr,
nullptr, 0,
nullptr}
1189 static PyTypeObject wrapper_type = {
1190 PyVarObject_HEAD_INIT(
nullptr, 0)
1192 sizeof(Dtool_SequenceWrapper),
1194 Dtool_WrapperBase_dealloc,
1199 Dtool_SequenceWrapper_repr,
1206 PyObject_GenericGetAttr,
1207 PyObject_GenericSetAttr,
1209 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_CHECKTYPES,
1226 PyType_GenericAlloc,
1238 static bool registered =
false;
1242 if (PyType_Ready(&wrapper_type) < 0) {
1247 _register_collection((PyTypeObject *)&wrapper_type,
"Sequence");
1250 (void)PyObject_INIT(wrap, &wrapper_type);
1252 wrap->_base._self =
self;
1253 wrap->_base._name = name;
1254 wrap->_len_func =
nullptr;
1255 wrap->_getitem_func =
nullptr;
1262 Dtool_MutableSequenceWrapper *Dtool_NewMutableSequenceWrapper(PyObject *
self,
const char *name) {
1263 Dtool_MutableSequenceWrapper *wrap = (Dtool_MutableSequenceWrapper *)PyObject_MALLOC(
sizeof(Dtool_MutableSequenceWrapper));
1264 if (wrap ==
nullptr) {
1265 return (Dtool_MutableSequenceWrapper *)PyErr_NoMemory();
1268 static PySequenceMethods seq_methods = {
1269 Dtool_SequenceWrapper_length,
1272 Dtool_SequenceWrapper_getitem,
1274 Dtool_MutableSequenceWrapper_setitem,
1276 Dtool_SequenceWrapper_contains,
1277 Dtool_MutableSequenceWrapper_extend,
1281 static PyMethodDef methods[] = {
1282 {
"index", &Dtool_SequenceWrapper_index, METH_O,
nullptr},
1283 {
"count", &Dtool_SequenceWrapper_count, METH_O,
nullptr},
1284 {
"clear", &Dtool_MutableSequenceWrapper_clear, METH_NOARGS,
nullptr},
1285 {
"pop", &Dtool_MutableSequenceWrapper_pop, METH_VARARGS,
nullptr},
1286 {
"remove", &Dtool_MutableSequenceWrapper_remove, METH_O,
nullptr},
1287 {
"append", &Dtool_MutableSequenceWrapper_append, METH_O,
nullptr},
1288 {
"insert", &Dtool_MutableSequenceWrapper_insert, METH_VARARGS,
nullptr},
1289 {
"extend", &Dtool_MutableSequenceWrapper_extend, METH_O,
nullptr},
1290 {
nullptr,
nullptr, 0,
nullptr}
1293 static PyTypeObject wrapper_type = {
1294 PyVarObject_HEAD_INIT(
nullptr, 0)
1296 sizeof(Dtool_MutableSequenceWrapper),
1298 Dtool_WrapperBase_dealloc,
1303 Dtool_SequenceWrapper_repr,
1310 PyObject_GenericGetAttr,
1311 PyObject_GenericSetAttr,
1313 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_CHECKTYPES,
1330 PyType_GenericAlloc,
1342 static bool registered =
false;
1346 if (PyType_Ready(&wrapper_type) < 0) {
1351 _register_collection((PyTypeObject *)&wrapper_type,
"MutableSequence");
1354 (void)PyObject_INIT(wrap, &wrapper_type);
1356 wrap->_base._self =
self;
1357 wrap->_base._name = name;
1358 wrap->_len_func =
nullptr;
1359 wrap->_getitem_func =
nullptr;
1360 wrap->_setitem_func =
nullptr;
1361 wrap->_insert_func =
nullptr;
1368 Dtool_MappingWrapper *Dtool_NewMappingWrapper(PyObject *
self,
const char *name) {
1369 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)PyObject_MALLOC(
sizeof(Dtool_MappingWrapper));
1370 if (wrap ==
nullptr) {
1371 return (Dtool_MappingWrapper *)PyErr_NoMemory();
1374 static PySequenceMethods seq_methods = {
1375 Dtool_SequenceWrapper_length,
1382 Dtool_MappingWrapper_contains,
1387 static PyMappingMethods map_methods = {
1388 Dtool_SequenceWrapper_length,
1389 Dtool_MappingWrapper_getitem,
1393 static PyMethodDef methods[] = {
1394 {
"get", &Dtool_MappingWrapper_get, METH_VARARGS,
nullptr},
1395 {
"keys", &Dtool_MappingWrapper_keys, METH_NOARGS,
nullptr},
1396 {
"values", &Dtool_MappingWrapper_values, METH_NOARGS,
nullptr},
1397 {
"items", &Dtool_MappingWrapper_items, METH_NOARGS,
nullptr},
1398 {
nullptr,
nullptr, 0,
nullptr}
1401 static PyTypeObject wrapper_type = {
1402 PyVarObject_HEAD_INIT(
nullptr, 0)
1404 sizeof(Dtool_MappingWrapper),
1406 Dtool_WrapperBase_dealloc,
1411 Dtool_WrapperBase_repr,
1418 PyObject_GenericGetAttr,
1419 PyObject_GenericSetAttr,
1421 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_CHECKTYPES,
1427 Dtool_MappingWrapper_iter,
1438 PyType_GenericAlloc,
1450 static bool registered =
false;
1454 if (PyType_Ready(&wrapper_type) < 0) {
1459 _register_collection((PyTypeObject *)&wrapper_type,
"Mapping");
1462 (void)PyObject_INIT(wrap, &wrapper_type);
1464 wrap->_base._self =
self;
1465 wrap->_base._name = name;
1466 wrap->_keys._len_func =
nullptr;
1467 wrap->_keys._getitem_func =
nullptr;
1468 wrap->_getitem_func =
nullptr;
1469 wrap->_setitem_func =
nullptr;
1476 Dtool_MappingWrapper *Dtool_NewMutableMappingWrapper(PyObject *
self,
const char *name) {
1477 Dtool_MappingWrapper *wrap = (Dtool_MappingWrapper *)PyObject_MALLOC(
sizeof(Dtool_MappingWrapper));
1478 if (wrap ==
nullptr) {
1479 return (Dtool_MappingWrapper *)PyErr_NoMemory();
1482 static PySequenceMethods seq_methods = {
1483 Dtool_SequenceWrapper_length,
1490 Dtool_MappingWrapper_contains,
1495 static PyMappingMethods map_methods = {
1496 Dtool_SequenceWrapper_length,
1497 Dtool_MappingWrapper_getitem,
1498 Dtool_MutableMappingWrapper_setitem,
1501 static PyMethodDef methods[] = {
1502 {
"get", &Dtool_MappingWrapper_get, METH_VARARGS,
nullptr},
1503 {
"pop", &Dtool_MutableMappingWrapper_pop, METH_VARARGS,
nullptr},
1504 {
"popitem", &Dtool_MutableMappingWrapper_popitem, METH_NOARGS,
nullptr},
1505 {
"clear", &Dtool_MutableMappingWrapper_clear, METH_VARARGS,
nullptr},
1506 {
"setdefault", &Dtool_MutableMappingWrapper_setdefault, METH_VARARGS,
nullptr},
1507 {
"update", (PyCFunction) &Dtool_MutableMappingWrapper_update, METH_VARARGS | METH_KEYWORDS,
nullptr},
1508 {
"keys", &Dtool_MappingWrapper_keys, METH_NOARGS,
nullptr},
1509 {
"values", &Dtool_MappingWrapper_values, METH_NOARGS,
nullptr},
1510 {
"items", &Dtool_MappingWrapper_items, METH_NOARGS,
nullptr},
1511 {
nullptr,
nullptr, 0,
nullptr}
1514 static PyTypeObject wrapper_type = {
1515 PyVarObject_HEAD_INIT(
nullptr, 0)
1517 sizeof(Dtool_MappingWrapper),
1519 Dtool_WrapperBase_dealloc,
1524 Dtool_WrapperBase_repr,
1531 PyObject_GenericGetAttr,
1532 PyObject_GenericSetAttr,
1534 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_CHECKTYPES,
1540 Dtool_MappingWrapper_iter,
1551 PyType_GenericAlloc,
1563 static bool registered =
false;
1567 if (PyType_Ready(&wrapper_type) < 0) {
1572 _register_collection((PyTypeObject *)&wrapper_type,
"MutableMapping");
1575 (void)PyObject_INIT(wrap, &wrapper_type);
1577 wrap->_base._self =
self;
1578 wrap->_base._name = name;
1579 wrap->_keys._len_func =
nullptr;
1580 wrap->_keys._getitem_func =
nullptr;
1581 wrap->_getitem_func =
nullptr;
1582 wrap->_setitem_func =
nullptr;
1590 Dtool_NewGenerator(PyObject *
self, iternextfunc gen_next) {
1591 static PyTypeObject wrapper_type = {
1592 PyVarObject_HEAD_INIT(
nullptr, 0)
1593 "generator wrapper",
1594 sizeof(Dtool_GeneratorWrapper),
1596 Dtool_WrapperBase_dealloc,
1608 PyObject_GenericGetAttr,
1609 PyObject_GenericSetAttr,
1611 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_CHECKTYPES,
1618 Dtool_GeneratorWrapper_iternext,
1628 PyType_GenericAlloc,
1640 if (PyType_Ready(&wrapper_type) < 0) {
1644 Dtool_GeneratorWrapper *gen;
1645 gen = (Dtool_GeneratorWrapper *)PyType_GenericAlloc(&wrapper_type, 0);
1646 if (gen !=
nullptr) {
1648 gen->_base._self =
self;
1649 gen->_iternext_func = gen_next;
1651 return (PyObject *)gen;
1659 Dtool_NewStaticProperty(PyTypeObject *type,
const PyGetSetDef *getset) {
1660 static PyTypeObject wrapper_type = {
1661 PyVarObject_HEAD_INIT(&PyType_Type, 0)
1662 "getset_descriptor",
1663 sizeof(PyGetSetDescrObject),
1665 (destructor)Dtool_StaticProperty_dealloc,
1670 (reprfunc)Dtool_StaticProperty_repr,
1677 PyObject_GenericGetAttr,
1682 Dtool_StaticProperty_traverse,
1693 (descrgetfunc)Dtool_StaticProperty_get,
1694 (descrsetfunc)Dtool_StaticProperty_set,
1709 if (PyType_Ready(&wrapper_type) < 0) {
1713 PyGetSetDescrObject *descr;
1714 descr = (PyGetSetDescrObject *)PyType_GenericAlloc(&wrapper_type, 0);
1715 if (descr !=
nullptr) {
1717 descr->d_getset = (PyGetSetDef *)getset;
1718 #if PY_MAJOR_VERSION >= 3 1719 descr->d_common.d_type = type;
1720 descr->d_common.d_name = PyUnicode_InternFromString(getset->name);
1721 #if PY_VERSION_HEX >= 0x03030000 1722 descr->d_common.d_qualname =
nullptr;
1725 descr->d_type = type;
1726 descr->d_name = PyString_InternFromString(getset->name);
1729 return (PyObject *)descr;
1732 #endif // HAVE_PYTHON
PyObject * Dtool_WrapValue(int value)
The following functions wrap an arbitrary C++ value into a PyObject.