blob: 4b985785f08f6aee942aa5bd6b6e59045bcffd2b [file] [log] [blame]
Tim Peters6d6c1a32001-08-02 04:15:00 +00001/* Descriptors -- a new, flexible way to describe attributes */
2
3#include "Python.h"
Victor Stinnerbcda8f12018-11-21 22:27:47 +01004#include "pycore_object.h"
Victor Stinner621cebe2018-11-12 16:53:38 +01005#include "pycore_pystate.h"
Victor Stinnerec13b932018-11-25 23:56:17 +01006#include "pycore_tupleobject.h"
Tim Peters6d6c1a32001-08-02 04:15:00 +00007#include "structmember.h" /* Why is this not included in Python.h? */
8
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02009/*[clinic input]
10class mappingproxy "mappingproxyobject *" "&PyDictProxy_Type"
11class property "propertyobject *" "&PyProperty_Type"
12[clinic start generated code]*/
13/*[clinic end generated code: output=da39a3ee5e6b4b0d input=556352653fd4c02e]*/
14
Tim Peters6d6c1a32001-08-02 04:15:00 +000015static void
16descr_dealloc(PyDescrObject *descr)
17{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000018 _PyObject_GC_UNTRACK(descr);
19 Py_XDECREF(descr->d_type);
20 Py_XDECREF(descr->d_name);
Antoine Pitrou9d574812011-12-12 13:47:25 +010021 Py_XDECREF(descr->d_qualname);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000022 PyObject_GC_Del(descr);
Tim Peters6d6c1a32001-08-02 04:15:00 +000023}
24
Walter Dörwaldd7fb7642007-06-11 16:36:59 +000025static PyObject *
Tim Peters6d6c1a32001-08-02 04:15:00 +000026descr_name(PyDescrObject *descr)
27{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000028 if (descr->d_name != NULL && PyUnicode_Check(descr->d_name))
29 return descr->d_name;
30 return NULL;
Tim Peters6d6c1a32001-08-02 04:15:00 +000031}
32
33static PyObject *
Serhiy Storchakaef1585e2015-12-25 20:01:53 +020034descr_repr(PyDescrObject *descr, const char *format)
Tim Peters6d6c1a32001-08-02 04:15:00 +000035{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000036 PyObject *name = NULL;
37 if (descr->d_name != NULL && PyUnicode_Check(descr->d_name))
38 name = descr->d_name;
Walter Dörwaldd7fb7642007-06-11 16:36:59 +000039
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000040 return PyUnicode_FromFormat(format, name, "?", descr->d_type->tp_name);
Tim Peters6d6c1a32001-08-02 04:15:00 +000041}
42
43static PyObject *
44method_repr(PyMethodDescrObject *descr)
45{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000046 return descr_repr((PyDescrObject *)descr,
47 "<method '%V' of '%s' objects>");
Tim Peters6d6c1a32001-08-02 04:15:00 +000048}
49
50static PyObject *
51member_repr(PyMemberDescrObject *descr)
52{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000053 return descr_repr((PyDescrObject *)descr,
54 "<member '%V' of '%s' objects>");
Tim Peters6d6c1a32001-08-02 04:15:00 +000055}
56
57static PyObject *
58getset_repr(PyGetSetDescrObject *descr)
59{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000060 return descr_repr((PyDescrObject *)descr,
61 "<attribute '%V' of '%s' objects>");
Tim Peters6d6c1a32001-08-02 04:15:00 +000062}
63
64static PyObject *
Armin Rigoc6686b72005-11-07 08:38:00 +000065wrapperdescr_repr(PyWrapperDescrObject *descr)
Tim Peters6d6c1a32001-08-02 04:15:00 +000066{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000067 return descr_repr((PyDescrObject *)descr,
68 "<slot wrapper '%V' of '%s' objects>");
Tim Peters6d6c1a32001-08-02 04:15:00 +000069}
70
71static int
Guido van Rossumb6e5a0c2003-02-11 18:44:42 +000072descr_check(PyDescrObject *descr, PyObject *obj, PyObject **pres)
Tim Peters6d6c1a32001-08-02 04:15:00 +000073{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000074 if (obj == NULL) {
75 Py_INCREF(descr);
76 *pres = (PyObject *)descr;
77 return 1;
78 }
79 if (!PyObject_TypeCheck(obj, descr->d_type)) {
80 PyErr_Format(PyExc_TypeError,
Inada Naoki62f95882019-04-01 17:56:11 +090081 "descriptor '%V' for '%.100s' objects "
82 "doesn't apply to a '%.100s' object",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000083 descr_name((PyDescrObject *)descr), "?",
84 descr->d_type->tp_name,
85 obj->ob_type->tp_name);
86 *pres = NULL;
87 return 1;
88 }
89 return 0;
Tim Peters6d6c1a32001-08-02 04:15:00 +000090}
91
92static PyObject *
Guido van Rossumb6e5a0c2003-02-11 18:44:42 +000093classmethod_get(PyMethodDescrObject *descr, PyObject *obj, PyObject *type)
Tim Petersbca1cbc2002-12-09 22:56:13 +000094{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000095 /* Ensure a valid type. Class methods ignore obj. */
96 if (type == NULL) {
97 if (obj != NULL)
98 type = (PyObject *)obj->ob_type;
99 else {
100 /* Wot - no type?! */
101 PyErr_Format(PyExc_TypeError,
Inada Naoki62f95882019-04-01 17:56:11 +0900102 "descriptor '%V' for type '%.100s' "
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000103 "needs either an object or a type",
104 descr_name((PyDescrObject *)descr), "?",
105 PyDescr_TYPE(descr)->tp_name);
106 return NULL;
107 }
108 }
109 if (!PyType_Check(type)) {
110 PyErr_Format(PyExc_TypeError,
Inada Naoki62f95882019-04-01 17:56:11 +0900111 "descriptor '%V' for type '%.100s' "
112 "needs a type, not a '%.100s' as arg 2",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000113 descr_name((PyDescrObject *)descr), "?",
114 PyDescr_TYPE(descr)->tp_name,
115 type->ob_type->tp_name);
116 return NULL;
117 }
118 if (!PyType_IsSubtype((PyTypeObject *)type, PyDescr_TYPE(descr))) {
119 PyErr_Format(PyExc_TypeError,
Inada Naoki62f95882019-04-01 17:56:11 +0900120 "descriptor '%V' requires a subtype of '%.100s' "
121 "but received '%.100s'",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000122 descr_name((PyDescrObject *)descr), "?",
123 PyDescr_TYPE(descr)->tp_name,
124 ((PyTypeObject *)type)->tp_name);
125 return NULL;
126 }
Andrew Svetlov3ba3a3e2012-12-25 13:32:35 +0200127 return PyCFunction_NewEx(descr->d_method, type, NULL);
Tim Petersbca1cbc2002-12-09 22:56:13 +0000128}
129
130static PyObject *
Guido van Rossumb6e5a0c2003-02-11 18:44:42 +0000131method_get(PyMethodDescrObject *descr, PyObject *obj, PyObject *type)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000132{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000133 PyObject *res;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000134
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000135 if (descr_check((PyDescrObject *)descr, obj, &res))
136 return res;
Andrew Svetlov3ba3a3e2012-12-25 13:32:35 +0200137 return PyCFunction_NewEx(descr->d_method, obj, NULL);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000138}
139
140static PyObject *
Guido van Rossumb6e5a0c2003-02-11 18:44:42 +0000141member_get(PyMemberDescrObject *descr, PyObject *obj, PyObject *type)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000142{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000143 PyObject *res;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000144
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000145 if (descr_check((PyDescrObject *)descr, obj, &res))
146 return res;
Steve Dowerb82e17e2019-05-23 08:45:22 -0700147
148 if (descr->d_member->flags & READ_RESTRICTED) {
149 if (PySys_Audit("object.__getattr__", "Os",
150 obj ? obj : Py_None, descr->d_member->name) < 0) {
151 return NULL;
152 }
153 }
154
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000155 return PyMember_GetOne((char *)obj, descr->d_member);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000156}
157
158static PyObject *
Guido van Rossumb6e5a0c2003-02-11 18:44:42 +0000159getset_get(PyGetSetDescrObject *descr, PyObject *obj, PyObject *type)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000160{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000161 PyObject *res;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000162
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000163 if (descr_check((PyDescrObject *)descr, obj, &res))
164 return res;
165 if (descr->d_getset->get != NULL)
166 return descr->d_getset->get(obj, descr->d_getset->closure);
167 PyErr_Format(PyExc_AttributeError,
168 "attribute '%V' of '%.100s' objects is not readable",
169 descr_name((PyDescrObject *)descr), "?",
170 PyDescr_TYPE(descr)->tp_name);
171 return NULL;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000172}
173
174static PyObject *
Armin Rigoc6686b72005-11-07 08:38:00 +0000175wrapperdescr_get(PyWrapperDescrObject *descr, PyObject *obj, PyObject *type)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000176{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000177 PyObject *res;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000178
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000179 if (descr_check((PyDescrObject *)descr, obj, &res))
180 return res;
181 return PyWrapper_New((PyObject *)descr, obj);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000182}
183
184static int
185descr_setcheck(PyDescrObject *descr, PyObject *obj, PyObject *value,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000186 int *pres)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000187{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000188 assert(obj != NULL);
189 if (!PyObject_TypeCheck(obj, descr->d_type)) {
190 PyErr_Format(PyExc_TypeError,
191 "descriptor '%V' for '%.100s' objects "
Inada Naoki62f95882019-04-01 17:56:11 +0900192 "doesn't apply to a '%.100s' object",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000193 descr_name(descr), "?",
194 descr->d_type->tp_name,
195 obj->ob_type->tp_name);
196 *pres = -1;
197 return 1;
198 }
199 return 0;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000200}
201
202static int
203member_set(PyMemberDescrObject *descr, PyObject *obj, PyObject *value)
204{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000205 int res;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000206
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000207 if (descr_setcheck((PyDescrObject *)descr, obj, value, &res))
208 return res;
209 return PyMember_SetOne((char *)obj, descr->d_member, value);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000210}
211
212static int
213getset_set(PyGetSetDescrObject *descr, PyObject *obj, PyObject *value)
214{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000215 int res;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000216
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000217 if (descr_setcheck((PyDescrObject *)descr, obj, value, &res))
218 return res;
219 if (descr->d_getset->set != NULL)
220 return descr->d_getset->set(obj, value,
221 descr->d_getset->closure);
222 PyErr_Format(PyExc_AttributeError,
223 "attribute '%V' of '%.100s' objects is not writable",
224 descr_name((PyDescrObject *)descr), "?",
225 PyDescr_TYPE(descr)->tp_name);
226 return -1;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000227}
228
229static PyObject *
Victor Stinnerc5257232017-01-18 10:38:09 +0100230methoddescr_call(PyMethodDescrObject *descr, PyObject *args, PyObject *kwargs)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000231{
Victor Stinnerc5257232017-01-18 10:38:09 +0100232 Py_ssize_t nargs;
233 PyObject *self, *result;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000234
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000235 /* Make sure that the first argument is acceptable as 'self' */
236 assert(PyTuple_Check(args));
Victor Stinnerc5257232017-01-18 10:38:09 +0100237 nargs = PyTuple_GET_SIZE(args);
238 if (nargs < 1) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000239 PyErr_Format(PyExc_TypeError,
240 "descriptor '%V' of '%.100s' "
241 "object needs an argument",
242 descr_name((PyDescrObject *)descr), "?",
243 PyDescr_TYPE(descr)->tp_name);
244 return NULL;
245 }
246 self = PyTuple_GET_ITEM(args, 0);
Victor Stinner3249dec2011-05-01 23:19:15 +0200247 if (!_PyObject_RealIsSubclass((PyObject *)Py_TYPE(self),
Victor Stinnerd9561312011-05-01 23:31:36 +0200248 (PyObject *)PyDescr_TYPE(descr))) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000249 PyErr_Format(PyExc_TypeError,
Inada Naoki62f95882019-04-01 17:56:11 +0900250 "descriptor '%V' for '%.100s' objects "
251 "doesn't apply to a '%.100s' object",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000252 descr_name((PyDescrObject *)descr), "?",
253 PyDescr_TYPE(descr)->tp_name,
254 self->ob_type->tp_name);
255 return NULL;
256 }
Tim Peters6d6c1a32001-08-02 04:15:00 +0000257
Victor Stinnerc5257232017-01-18 10:38:09 +0100258 result = _PyMethodDef_RawFastCallDict(descr->d_method, self,
Victor Stinnerd17a6932018-11-09 16:56:48 +0100259 &_PyTuple_ITEMS(args)[1], nargs - 1,
Victor Stinnerc5257232017-01-18 10:38:09 +0100260 kwargs);
261 result = _Py_CheckFunctionResult((PyObject *)descr, result, NULL);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000262 return result;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000263}
264
INADA Naoki5566bbb2017-02-03 07:43:03 +0900265// same to methoddescr_call(), but use FASTCALL convention.
266PyObject *
Jeroen Demeyer37788bc2019-05-30 15:11:22 +0200267_PyMethodDescr_Vectorcall(PyObject *descrobj,
268 PyObject *const *args, size_t nargsf,
269 PyObject *kwnames)
INADA Naoki5566bbb2017-02-03 07:43:03 +0900270{
271 assert(Py_TYPE(descrobj) == &PyMethodDescr_Type);
272 PyMethodDescrObject *descr = (PyMethodDescrObject *)descrobj;
273 PyObject *self, *result;
274
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200275 Py_ssize_t nargs = PyVectorcall_NARGS(nargsf);
INADA Naoki5566bbb2017-02-03 07:43:03 +0900276 /* Make sure that the first argument is acceptable as 'self' */
277 if (nargs < 1) {
278 PyErr_Format(PyExc_TypeError,
279 "descriptor '%V' of '%.100s' "
280 "object needs an argument",
281 descr_name((PyDescrObject *)descr), "?",
282 PyDescr_TYPE(descr)->tp_name);
283 return NULL;
284 }
285 self = args[0];
286 if (!_PyObject_RealIsSubclass((PyObject *)Py_TYPE(self),
287 (PyObject *)PyDescr_TYPE(descr))) {
288 PyErr_Format(PyExc_TypeError,
Inada Naoki62f95882019-04-01 17:56:11 +0900289 "descriptor '%V' for '%.100s' objects "
290 "doesn't apply to a '%.100s' object",
INADA Naoki5566bbb2017-02-03 07:43:03 +0900291 descr_name((PyDescrObject *)descr), "?",
292 PyDescr_TYPE(descr)->tp_name,
293 self->ob_type->tp_name);
294 return NULL;
295 }
296
297 result = _PyMethodDef_RawFastCallKeywords(descr->d_method, self,
298 args+1, nargs-1, kwnames);
299 result = _Py_CheckFunctionResult((PyObject *)descr, result, NULL);
300 return result;
301}
302
Jeroen Demeyer3f345c32019-06-07 12:20:24 +0200303/* Instances of classmethod_descriptor are unlikely to be called directly.
304 For one, the analogous class "classmethod" (for Python classes) is not
305 callable. Second, users are not likely to access a classmethod_descriptor
306 directly, since it means pulling it from the class __dict__.
307
308 This is just an excuse to say that this doesn't need to be optimized:
309 we implement this simply by calling __get__ and then calling the result.
310*/
Tim Peters6d6c1a32001-08-02 04:15:00 +0000311static PyObject *
Tim Petersbca1cbc2002-12-09 22:56:13 +0000312classmethoddescr_call(PyMethodDescrObject *descr, PyObject *args,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000313 PyObject *kwds)
Tim Petersbca1cbc2002-12-09 22:56:13 +0000314{
Jeroen Demeyer3f345c32019-06-07 12:20:24 +0200315 Py_ssize_t argc = PyTuple_GET_SIZE(args);
Benjamin Peterson7295c6a2012-05-01 09:51:09 -0400316 if (argc < 1) {
317 PyErr_Format(PyExc_TypeError,
318 "descriptor '%V' of '%.100s' "
319 "object needs an argument",
320 descr_name((PyDescrObject *)descr), "?",
321 PyDescr_TYPE(descr)->tp_name);
322 return NULL;
323 }
Jeroen Demeyer3f345c32019-06-07 12:20:24 +0200324 PyObject *self = PyTuple_GET_ITEM(args, 0);
325 PyObject *bound = classmethod_get(descr, NULL, self);
326 if (bound == NULL) {
Benjamin Peterson7295c6a2012-05-01 09:51:09 -0400327 return NULL;
328 }
Jeroen Demeyer3f345c32019-06-07 12:20:24 +0200329 PyObject *res = _PyObject_FastCallDict(bound, _PyTuple_ITEMS(args)+1,
330 argc-1, kwds);
331 Py_DECREF(bound);
332 return res;
Tim Petersbca1cbc2002-12-09 22:56:13 +0000333}
334
Serhiy Storchaka5e02c782017-09-21 14:25:36 +0300335Py_LOCAL_INLINE(PyObject *)
336wrapperdescr_raw_call(PyWrapperDescrObject *descr, PyObject *self,
337 PyObject *args, PyObject *kwds)
338{
339 wrapperfunc wrapper = descr->d_base->wrapper;
340
341 if (descr->d_base->flags & PyWrapperFlag_KEYWORDS) {
Serhiy Storchaka1c607152018-11-27 21:34:27 +0200342 wrapperfunc_kwds wk = (wrapperfunc_kwds)(void(*)(void))wrapper;
Serhiy Storchaka5e02c782017-09-21 14:25:36 +0300343 return (*wk)(self, args, descr->d_wrapped, kwds);
344 }
345
346 if (kwds != NULL && (!PyDict_Check(kwds) || PyDict_GET_SIZE(kwds) != 0)) {
347 PyErr_Format(PyExc_TypeError,
348 "wrapper %s() takes no keyword arguments",
349 descr->d_base->name);
350 return NULL;
351 }
352 return (*wrapper)(self, args, descr->d_wrapped);
353}
354
Tim Petersbca1cbc2002-12-09 22:56:13 +0000355static PyObject *
Tim Peters6d6c1a32001-08-02 04:15:00 +0000356wrapperdescr_call(PyWrapperDescrObject *descr, PyObject *args, PyObject *kwds)
357{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000358 Py_ssize_t argc;
Serhiy Storchaka5e02c782017-09-21 14:25:36 +0300359 PyObject *self, *result;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000360
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000361 /* Make sure that the first argument is acceptable as 'self' */
362 assert(PyTuple_Check(args));
363 argc = PyTuple_GET_SIZE(args);
364 if (argc < 1) {
365 PyErr_Format(PyExc_TypeError,
366 "descriptor '%V' of '%.100s' "
367 "object needs an argument",
368 descr_name((PyDescrObject *)descr), "?",
369 PyDescr_TYPE(descr)->tp_name);
370 return NULL;
371 }
372 self = PyTuple_GET_ITEM(args, 0);
Victor Stinner3249dec2011-05-01 23:19:15 +0200373 if (!_PyObject_RealIsSubclass((PyObject *)Py_TYPE(self),
Victor Stinnerd9561312011-05-01 23:31:36 +0200374 (PyObject *)PyDescr_TYPE(descr))) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000375 PyErr_Format(PyExc_TypeError,
376 "descriptor '%V' "
377 "requires a '%.100s' object "
378 "but received a '%.100s'",
379 descr_name((PyDescrObject *)descr), "?",
380 PyDescr_TYPE(descr)->tp_name,
381 self->ob_type->tp_name);
382 return NULL;
383 }
Tim Peters6d6c1a32001-08-02 04:15:00 +0000384
Serhiy Storchaka5e02c782017-09-21 14:25:36 +0300385 args = PyTuple_GetSlice(args, 1, argc);
386 if (args == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000387 return NULL;
Serhiy Storchaka5e02c782017-09-21 14:25:36 +0300388 }
389 result = wrapperdescr_raw_call(descr, self, args, kwds);
390 Py_DECREF(args);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000391 return result;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000392}
393
Serhiy Storchaka5e02c782017-09-21 14:25:36 +0300394
Tim Peters6d6c1a32001-08-02 04:15:00 +0000395static PyObject *
Guido van Rossum6f799372001-09-20 20:46:19 +0000396method_get_doc(PyMethodDescrObject *descr, void *closure)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000397{
Larry Hastings2623c8c2014-02-08 22:15:29 -0800398 return _PyType_GetDocFromInternalDoc(descr->d_method->ml_name, descr->d_method->ml_doc);
Larry Hastings5c661892014-01-24 06:17:25 -0800399}
400
401static PyObject *
402method_get_text_signature(PyMethodDescrObject *descr, void *closure)
403{
Larry Hastings2623c8c2014-02-08 22:15:29 -0800404 return _PyType_GetTextSignatureFromInternalDoc(descr->d_method->ml_name, descr->d_method->ml_doc);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000405}
406
Antoine Pitrou9d574812011-12-12 13:47:25 +0100407static PyObject *
408calculate_qualname(PyDescrObject *descr)
409{
410 PyObject *type_qualname, *res;
411 _Py_IDENTIFIER(__qualname__);
412
413 if (descr->d_name == NULL || !PyUnicode_Check(descr->d_name)) {
414 PyErr_SetString(PyExc_TypeError,
415 "<descriptor>.__name__ is not a unicode object");
416 return NULL;
417 }
418
419 type_qualname = _PyObject_GetAttrId((PyObject *)descr->d_type,
420 &PyId___qualname__);
421 if (type_qualname == NULL)
422 return NULL;
423
424 if (!PyUnicode_Check(type_qualname)) {
425 PyErr_SetString(PyExc_TypeError, "<descriptor>.__objclass__."
426 "__qualname__ is not a unicode object");
427 Py_XDECREF(type_qualname);
428 return NULL;
429 }
430
431 res = PyUnicode_FromFormat("%S.%S", type_qualname, descr->d_name);
432 Py_DECREF(type_qualname);
433 return res;
434}
435
436static PyObject *
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +0200437descr_get_qualname(PyDescrObject *descr, void *Py_UNUSED(ignored))
Antoine Pitrou9d574812011-12-12 13:47:25 +0100438{
439 if (descr->d_qualname == NULL)
440 descr->d_qualname = calculate_qualname(descr);
441 Py_XINCREF(descr->d_qualname);
442 return descr->d_qualname;
443}
444
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +0100445static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +0530446descr_reduce(PyDescrObject *descr, PyObject *Py_UNUSED(ignored))
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +0100447{
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +0100448 _Py_IDENTIFIER(getattr);
Serhiy Storchakabb86bf42018-12-11 08:28:18 +0200449 return Py_BuildValue("N(OO)", _PyEval_GetBuiltinId(&PyId_getattr),
450 PyDescr_TYPE(descr), PyDescr_NAME(descr));
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +0100451}
452
453static PyMethodDef descr_methods[] = {
454 {"__reduce__", (PyCFunction)descr_reduce, METH_NOARGS, NULL},
455 {NULL, NULL}
456};
457
Guido van Rossum6f799372001-09-20 20:46:19 +0000458static PyMemberDef descr_members[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000459 {"__objclass__", T_OBJECT, offsetof(PyDescrObject, d_type), READONLY},
460 {"__name__", T_OBJECT, offsetof(PyDescrObject, d_name), READONLY},
461 {0}
Tim Peters6d6c1a32001-08-02 04:15:00 +0000462};
463
Guido van Rossum32d34c82001-09-20 21:45:26 +0000464static PyGetSetDef method_getset[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000465 {"__doc__", (getter)method_get_doc},
Antoine Pitrou9d574812011-12-12 13:47:25 +0100466 {"__qualname__", (getter)descr_get_qualname},
Larry Hastings5c661892014-01-24 06:17:25 -0800467 {"__text_signature__", (getter)method_get_text_signature},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000468 {0}
Guido van Rossum6f799372001-09-20 20:46:19 +0000469};
470
471static PyObject *
472member_get_doc(PyMemberDescrObject *descr, void *closure)
473{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000474 if (descr->d_member->doc == NULL) {
Serhiy Storchaka228b12e2017-01-23 09:47:21 +0200475 Py_RETURN_NONE;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000476 }
477 return PyUnicode_FromString(descr->d_member->doc);
Guido van Rossum6f799372001-09-20 20:46:19 +0000478}
479
Guido van Rossum32d34c82001-09-20 21:45:26 +0000480static PyGetSetDef member_getset[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000481 {"__doc__", (getter)member_get_doc},
Antoine Pitrou9d574812011-12-12 13:47:25 +0100482 {"__qualname__", (getter)descr_get_qualname},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000483 {0}
Tim Peters6d6c1a32001-08-02 04:15:00 +0000484};
485
486static PyObject *
Guido van Rossum32d34c82001-09-20 21:45:26 +0000487getset_get_doc(PyGetSetDescrObject *descr, void *closure)
488{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000489 if (descr->d_getset->doc == NULL) {
Serhiy Storchaka228b12e2017-01-23 09:47:21 +0200490 Py_RETURN_NONE;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000491 }
492 return PyUnicode_FromString(descr->d_getset->doc);
Guido van Rossum32d34c82001-09-20 21:45:26 +0000493}
494
495static PyGetSetDef getset_getset[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000496 {"__doc__", (getter)getset_get_doc},
Antoine Pitrou9d574812011-12-12 13:47:25 +0100497 {"__qualname__", (getter)descr_get_qualname},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000498 {0}
Guido van Rossum32d34c82001-09-20 21:45:26 +0000499};
500
501static PyObject *
Armin Rigoc6686b72005-11-07 08:38:00 +0000502wrapperdescr_get_doc(PyWrapperDescrObject *descr, void *closure)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000503{
Larry Hastings2623c8c2014-02-08 22:15:29 -0800504 return _PyType_GetDocFromInternalDoc(descr->d_base->name, descr->d_base->doc);
Larry Hastings5c661892014-01-24 06:17:25 -0800505}
506
507static PyObject *
508wrapperdescr_get_text_signature(PyWrapperDescrObject *descr, void *closure)
509{
Larry Hastings2623c8c2014-02-08 22:15:29 -0800510 return _PyType_GetTextSignatureFromInternalDoc(descr->d_base->name, descr->d_base->doc);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000511}
512
Armin Rigoc6686b72005-11-07 08:38:00 +0000513static PyGetSetDef wrapperdescr_getset[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000514 {"__doc__", (getter)wrapperdescr_get_doc},
Antoine Pitrou9d574812011-12-12 13:47:25 +0100515 {"__qualname__", (getter)descr_get_qualname},
Larry Hastings5c661892014-01-24 06:17:25 -0800516 {"__text_signature__", (getter)wrapperdescr_get_text_signature},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000517 {0}
Tim Peters6d6c1a32001-08-02 04:15:00 +0000518};
519
Guido van Rossum048eb752001-10-02 21:24:57 +0000520static int
521descr_traverse(PyObject *self, visitproc visit, void *arg)
522{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000523 PyDescrObject *descr = (PyDescrObject *)self;
524 Py_VISIT(descr->d_type);
525 return 0;
Guido van Rossum048eb752001-10-02 21:24:57 +0000526}
527
Christian Heimesa22e8bd2007-11-29 22:35:39 +0000528PyTypeObject PyMethodDescr_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000529 PyVarObject_HEAD_INIT(&PyType_Type, 0)
530 "method_descriptor",
531 sizeof(PyMethodDescrObject),
532 0,
533 (destructor)descr_dealloc, /* tp_dealloc */
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200534 offsetof(PyMethodDescrObject, vectorcall), /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000535 0, /* tp_getattr */
536 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +0200537 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000538 (reprfunc)method_repr, /* tp_repr */
539 0, /* tp_as_number */
540 0, /* tp_as_sequence */
541 0, /* tp_as_mapping */
542 0, /* tp_hash */
543 (ternaryfunc)methoddescr_call, /* tp_call */
544 0, /* tp_str */
545 PyObject_GenericGetAttr, /* tp_getattro */
546 0, /* tp_setattro */
547 0, /* tp_as_buffer */
Jeroen Demeyereb65e242019-05-28 14:42:53 +0200548 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC |
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200549 _Py_TPFLAGS_HAVE_VECTORCALL |
Jeroen Demeyereb65e242019-05-28 14:42:53 +0200550 Py_TPFLAGS_METHOD_DESCRIPTOR, /* tp_flags */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000551 0, /* tp_doc */
552 descr_traverse, /* tp_traverse */
553 0, /* tp_clear */
554 0, /* tp_richcompare */
555 0, /* tp_weaklistoffset */
556 0, /* tp_iter */
557 0, /* tp_iternext */
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +0100558 descr_methods, /* tp_methods */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000559 descr_members, /* tp_members */
560 method_getset, /* tp_getset */
561 0, /* tp_base */
562 0, /* tp_dict */
563 (descrgetfunc)method_get, /* tp_descr_get */
564 0, /* tp_descr_set */
Tim Peters6d6c1a32001-08-02 04:15:00 +0000565};
566
Guido van Rossumb6e5a0c2003-02-11 18:44:42 +0000567/* This is for METH_CLASS in C, not for "f = classmethod(f)" in Python! */
Christian Heimesa22e8bd2007-11-29 22:35:39 +0000568PyTypeObject PyClassMethodDescr_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000569 PyVarObject_HEAD_INIT(&PyType_Type, 0)
570 "classmethod_descriptor",
571 sizeof(PyMethodDescrObject),
572 0,
573 (destructor)descr_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +0200574 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000575 0, /* tp_getattr */
576 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +0200577 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000578 (reprfunc)method_repr, /* tp_repr */
579 0, /* tp_as_number */
580 0, /* tp_as_sequence */
581 0, /* tp_as_mapping */
582 0, /* tp_hash */
583 (ternaryfunc)classmethoddescr_call, /* tp_call */
584 0, /* tp_str */
585 PyObject_GenericGetAttr, /* tp_getattro */
586 0, /* tp_setattro */
587 0, /* tp_as_buffer */
588 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /* tp_flags */
589 0, /* tp_doc */
590 descr_traverse, /* tp_traverse */
591 0, /* tp_clear */
592 0, /* tp_richcompare */
593 0, /* tp_weaklistoffset */
594 0, /* tp_iter */
595 0, /* tp_iternext */
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +0100596 descr_methods, /* tp_methods */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000597 descr_members, /* tp_members */
598 method_getset, /* tp_getset */
599 0, /* tp_base */
600 0, /* tp_dict */
601 (descrgetfunc)classmethod_get, /* tp_descr_get */
602 0, /* tp_descr_set */
Tim Petersbca1cbc2002-12-09 22:56:13 +0000603};
604
Christian Heimesa22e8bd2007-11-29 22:35:39 +0000605PyTypeObject PyMemberDescr_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000606 PyVarObject_HEAD_INIT(&PyType_Type, 0)
607 "member_descriptor",
608 sizeof(PyMemberDescrObject),
609 0,
610 (destructor)descr_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +0200611 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000612 0, /* tp_getattr */
613 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +0200614 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000615 (reprfunc)member_repr, /* tp_repr */
616 0, /* tp_as_number */
617 0, /* tp_as_sequence */
618 0, /* tp_as_mapping */
619 0, /* tp_hash */
620 0, /* tp_call */
621 0, /* tp_str */
622 PyObject_GenericGetAttr, /* tp_getattro */
623 0, /* tp_setattro */
624 0, /* tp_as_buffer */
625 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /* tp_flags */
626 0, /* tp_doc */
627 descr_traverse, /* tp_traverse */
628 0, /* tp_clear */
629 0, /* tp_richcompare */
630 0, /* tp_weaklistoffset */
631 0, /* tp_iter */
632 0, /* tp_iternext */
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +0100633 descr_methods, /* tp_methods */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000634 descr_members, /* tp_members */
635 member_getset, /* tp_getset */
636 0, /* tp_base */
637 0, /* tp_dict */
638 (descrgetfunc)member_get, /* tp_descr_get */
639 (descrsetfunc)member_set, /* tp_descr_set */
Tim Peters6d6c1a32001-08-02 04:15:00 +0000640};
641
Christian Heimesa22e8bd2007-11-29 22:35:39 +0000642PyTypeObject PyGetSetDescr_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000643 PyVarObject_HEAD_INIT(&PyType_Type, 0)
644 "getset_descriptor",
645 sizeof(PyGetSetDescrObject),
646 0,
647 (destructor)descr_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +0200648 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000649 0, /* tp_getattr */
650 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +0200651 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000652 (reprfunc)getset_repr, /* tp_repr */
653 0, /* tp_as_number */
654 0, /* tp_as_sequence */
655 0, /* tp_as_mapping */
656 0, /* tp_hash */
657 0, /* tp_call */
658 0, /* tp_str */
659 PyObject_GenericGetAttr, /* tp_getattro */
660 0, /* tp_setattro */
661 0, /* tp_as_buffer */
662 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /* tp_flags */
663 0, /* tp_doc */
664 descr_traverse, /* tp_traverse */
665 0, /* tp_clear */
666 0, /* tp_richcompare */
667 0, /* tp_weaklistoffset */
668 0, /* tp_iter */
669 0, /* tp_iternext */
670 0, /* tp_methods */
671 descr_members, /* tp_members */
672 getset_getset, /* tp_getset */
673 0, /* tp_base */
674 0, /* tp_dict */
675 (descrgetfunc)getset_get, /* tp_descr_get */
676 (descrsetfunc)getset_set, /* tp_descr_set */
Tim Peters6d6c1a32001-08-02 04:15:00 +0000677};
678
Guido van Rossumf4593e02001-10-03 12:09:30 +0000679PyTypeObject PyWrapperDescr_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000680 PyVarObject_HEAD_INIT(&PyType_Type, 0)
681 "wrapper_descriptor",
682 sizeof(PyWrapperDescrObject),
683 0,
684 (destructor)descr_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +0200685 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000686 0, /* tp_getattr */
687 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +0200688 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000689 (reprfunc)wrapperdescr_repr, /* tp_repr */
690 0, /* tp_as_number */
691 0, /* tp_as_sequence */
692 0, /* tp_as_mapping */
693 0, /* tp_hash */
694 (ternaryfunc)wrapperdescr_call, /* tp_call */
695 0, /* tp_str */
696 PyObject_GenericGetAttr, /* tp_getattro */
697 0, /* tp_setattro */
698 0, /* tp_as_buffer */
Jeroen Demeyereb65e242019-05-28 14:42:53 +0200699 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC |
700 Py_TPFLAGS_METHOD_DESCRIPTOR, /* tp_flags */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000701 0, /* tp_doc */
702 descr_traverse, /* tp_traverse */
703 0, /* tp_clear */
704 0, /* tp_richcompare */
705 0, /* tp_weaklistoffset */
706 0, /* tp_iter */
707 0, /* tp_iternext */
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +0100708 descr_methods, /* tp_methods */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000709 descr_members, /* tp_members */
710 wrapperdescr_getset, /* tp_getset */
711 0, /* tp_base */
712 0, /* tp_dict */
713 (descrgetfunc)wrapperdescr_get, /* tp_descr_get */
714 0, /* tp_descr_set */
Tim Peters6d6c1a32001-08-02 04:15:00 +0000715};
716
717static PyDescrObject *
Jeremy Hyltonaf68c872005-12-10 18:50:16 +0000718descr_new(PyTypeObject *descrtype, PyTypeObject *type, const char *name)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000719{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000720 PyDescrObject *descr;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000721
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000722 descr = (PyDescrObject *)PyType_GenericAlloc(descrtype, 0);
723 if (descr != NULL) {
724 Py_XINCREF(type);
725 descr->d_type = type;
726 descr->d_name = PyUnicode_InternFromString(name);
727 if (descr->d_name == NULL) {
728 Py_DECREF(descr);
729 descr = NULL;
730 }
Benjamin Petersonf2fe7f02011-12-17 08:02:20 -0500731 else {
732 descr->d_qualname = NULL;
733 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000734 }
735 return descr;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000736}
737
738PyObject *
739PyDescr_NewMethod(PyTypeObject *type, PyMethodDef *method)
740{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000741 PyMethodDescrObject *descr;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000742
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000743 descr = (PyMethodDescrObject *)descr_new(&PyMethodDescr_Type,
744 type, method->ml_name);
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200745 if (descr != NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000746 descr->d_method = method;
Jeroen Demeyer37788bc2019-05-30 15:11:22 +0200747 descr->vectorcall = _PyMethodDescr_Vectorcall;
Jeroen Demeyeraacc77f2019-05-29 20:31:52 +0200748 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000749 return (PyObject *)descr;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000750}
751
752PyObject *
Tim Petersbca1cbc2002-12-09 22:56:13 +0000753PyDescr_NewClassMethod(PyTypeObject *type, PyMethodDef *method)
754{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000755 PyMethodDescrObject *descr;
Tim Petersbca1cbc2002-12-09 22:56:13 +0000756
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000757 descr = (PyMethodDescrObject *)descr_new(&PyClassMethodDescr_Type,
758 type, method->ml_name);
759 if (descr != NULL)
760 descr->d_method = method;
761 return (PyObject *)descr;
Tim Petersbca1cbc2002-12-09 22:56:13 +0000762}
763
764PyObject *
Guido van Rossum6f799372001-09-20 20:46:19 +0000765PyDescr_NewMember(PyTypeObject *type, PyMemberDef *member)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000766{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000767 PyMemberDescrObject *descr;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000768
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000769 descr = (PyMemberDescrObject *)descr_new(&PyMemberDescr_Type,
770 type, member->name);
771 if (descr != NULL)
772 descr->d_member = member;
773 return (PyObject *)descr;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000774}
775
776PyObject *
Guido van Rossum32d34c82001-09-20 21:45:26 +0000777PyDescr_NewGetSet(PyTypeObject *type, PyGetSetDef *getset)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000778{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000779 PyGetSetDescrObject *descr;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000780
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000781 descr = (PyGetSetDescrObject *)descr_new(&PyGetSetDescr_Type,
782 type, getset->name);
783 if (descr != NULL)
784 descr->d_getset = getset;
785 return (PyObject *)descr;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000786}
787
788PyObject *
789PyDescr_NewWrapper(PyTypeObject *type, struct wrapperbase *base, void *wrapped)
790{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000791 PyWrapperDescrObject *descr;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000792
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000793 descr = (PyWrapperDescrObject *)descr_new(&PyWrapperDescr_Type,
794 type, base->name);
795 if (descr != NULL) {
796 descr->d_base = base;
797 descr->d_wrapped = wrapped;
798 }
799 return (PyObject *)descr;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000800}
801
Tim Peters6d6c1a32001-08-02 04:15:00 +0000802
Victor Stinner0db176f2012-04-16 00:16:30 +0200803/* --- mappingproxy: read-only proxy for mappings --- */
Tim Peters6d6c1a32001-08-02 04:15:00 +0000804
805/* This has no reason to be in this file except that adding new files is a
806 bit of a pain */
807
808typedef struct {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000809 PyObject_HEAD
Victor Stinner0db176f2012-04-16 00:16:30 +0200810 PyObject *mapping;
811} mappingproxyobject;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000812
Martin v. Löwis18e16552006-02-15 17:27:45 +0000813static Py_ssize_t
Victor Stinner0db176f2012-04-16 00:16:30 +0200814mappingproxy_len(mappingproxyobject *pp)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000815{
Victor Stinner0db176f2012-04-16 00:16:30 +0200816 return PyObject_Size(pp->mapping);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000817}
818
819static PyObject *
Victor Stinner0db176f2012-04-16 00:16:30 +0200820mappingproxy_getitem(mappingproxyobject *pp, PyObject *key)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000821{
Victor Stinner0db176f2012-04-16 00:16:30 +0200822 return PyObject_GetItem(pp->mapping, key);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000823}
824
Victor Stinner0db176f2012-04-16 00:16:30 +0200825static PyMappingMethods mappingproxy_as_mapping = {
826 (lenfunc)mappingproxy_len, /* mp_length */
827 (binaryfunc)mappingproxy_getitem, /* mp_subscript */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000828 0, /* mp_ass_subscript */
Tim Peters6d6c1a32001-08-02 04:15:00 +0000829};
830
831static int
Victor Stinner0db176f2012-04-16 00:16:30 +0200832mappingproxy_contains(mappingproxyobject *pp, PyObject *key)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000833{
Victor Stinner0db176f2012-04-16 00:16:30 +0200834 if (PyDict_CheckExact(pp->mapping))
835 return PyDict_Contains(pp->mapping, key);
836 else
837 return PySequence_Contains(pp->mapping, key);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000838}
839
Victor Stinner0db176f2012-04-16 00:16:30 +0200840static PySequenceMethods mappingproxy_as_sequence = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000841 0, /* sq_length */
842 0, /* sq_concat */
843 0, /* sq_repeat */
844 0, /* sq_item */
845 0, /* sq_slice */
846 0, /* sq_ass_item */
847 0, /* sq_ass_slice */
Victor Stinner0db176f2012-04-16 00:16:30 +0200848 (objobjproc)mappingproxy_contains, /* sq_contains */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000849 0, /* sq_inplace_concat */
850 0, /* sq_inplace_repeat */
Tim Peters6d6c1a32001-08-02 04:15:00 +0000851};
852
853static PyObject *
Jeroen Demeyerb1263d52019-06-28 11:49:00 +0200854mappingproxy_get(mappingproxyobject *pp, PyObject *const *args, Py_ssize_t nargs)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000855{
Jeroen Demeyerb1263d52019-06-28 11:49:00 +0200856 /* newargs: mapping, key, default=None */
857 PyObject *newargs[3];
858 newargs[0] = pp->mapping;
859 newargs[2] = Py_None;
Tim Peters6d6c1a32001-08-02 04:15:00 +0000860
Jeroen Demeyerb1263d52019-06-28 11:49:00 +0200861 if (!_PyArg_UnpackStack(args, nargs, "get", 1, 2,
862 &newargs[1], &newargs[2]))
863 {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000864 return NULL;
Jeroen Demeyerb1263d52019-06-28 11:49:00 +0200865 }
866 _Py_IDENTIFIER(get);
867 return _PyObject_VectorcallMethodId(&PyId_get, newargs,
868 3 | PY_VECTORCALL_ARGUMENTS_OFFSET,
869 NULL);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000870}
871
872static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +0530873mappingproxy_keys(mappingproxyobject *pp, PyObject *Py_UNUSED(ignored))
Tim Peters6d6c1a32001-08-02 04:15:00 +0000874{
Martin v. Löwisbd928fe2011-10-14 10:20:37 +0200875 _Py_IDENTIFIER(keys);
Victor Stinner0db176f2012-04-16 00:16:30 +0200876 return _PyObject_CallMethodId(pp->mapping, &PyId_keys, NULL);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000877}
878
879static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +0530880mappingproxy_values(mappingproxyobject *pp, PyObject *Py_UNUSED(ignored))
Tim Peters6d6c1a32001-08-02 04:15:00 +0000881{
Martin v. Löwisbd928fe2011-10-14 10:20:37 +0200882 _Py_IDENTIFIER(values);
Victor Stinner0db176f2012-04-16 00:16:30 +0200883 return _PyObject_CallMethodId(pp->mapping, &PyId_values, NULL);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000884}
885
886static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +0530887mappingproxy_items(mappingproxyobject *pp, PyObject *Py_UNUSED(ignored))
Tim Peters6d6c1a32001-08-02 04:15:00 +0000888{
Martin v. Löwisbd928fe2011-10-14 10:20:37 +0200889 _Py_IDENTIFIER(items);
Victor Stinner0db176f2012-04-16 00:16:30 +0200890 return _PyObject_CallMethodId(pp->mapping, &PyId_items, NULL);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000891}
892
893static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +0530894mappingproxy_copy(mappingproxyobject *pp, PyObject *Py_UNUSED(ignored))
Tim Peters6d6c1a32001-08-02 04:15:00 +0000895{
Martin v. Löwisbd928fe2011-10-14 10:20:37 +0200896 _Py_IDENTIFIER(copy);
Victor Stinner0db176f2012-04-16 00:16:30 +0200897 return _PyObject_CallMethodId(pp->mapping, &PyId_copy, NULL);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000898}
899
Victor Stinner0db176f2012-04-16 00:16:30 +0200900/* WARNING: mappingproxy methods must not give access
901 to the underlying mapping */
902
903static PyMethodDef mappingproxy_methods[] = {
Jeroen Demeyerb1263d52019-06-28 11:49:00 +0200904 {"get", (PyCFunction)mappingproxy_get, METH_FASTCALL,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000905 PyDoc_STR("D.get(k[,d]) -> D[k] if k in D, else d."
Victor Stinner0db176f2012-04-16 00:16:30 +0200906 " d defaults to None.")},
907 {"keys", (PyCFunction)mappingproxy_keys, METH_NOARGS,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000908 PyDoc_STR("D.keys() -> list of D's keys")},
Victor Stinner0db176f2012-04-16 00:16:30 +0200909 {"values", (PyCFunction)mappingproxy_values, METH_NOARGS,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000910 PyDoc_STR("D.values() -> list of D's values")},
Victor Stinner0db176f2012-04-16 00:16:30 +0200911 {"items", (PyCFunction)mappingproxy_items, METH_NOARGS,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000912 PyDoc_STR("D.items() -> list of D's (key, value) pairs, as 2-tuples")},
Victor Stinner0db176f2012-04-16 00:16:30 +0200913 {"copy", (PyCFunction)mappingproxy_copy, METH_NOARGS,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000914 PyDoc_STR("D.copy() -> a shallow copy of D")},
915 {0}
Tim Peters6d6c1a32001-08-02 04:15:00 +0000916};
917
918static void
Victor Stinner0db176f2012-04-16 00:16:30 +0200919mappingproxy_dealloc(mappingproxyobject *pp)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000920{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000921 _PyObject_GC_UNTRACK(pp);
Victor Stinner0db176f2012-04-16 00:16:30 +0200922 Py_DECREF(pp->mapping);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000923 PyObject_GC_Del(pp);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000924}
925
926static PyObject *
Victor Stinner0db176f2012-04-16 00:16:30 +0200927mappingproxy_getiter(mappingproxyobject *pp)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000928{
Victor Stinner0db176f2012-04-16 00:16:30 +0200929 return PyObject_GetIter(pp->mapping);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000930}
931
Neil Schemenauer26775122001-10-21 22:26:43 +0000932static PyObject *
Victor Stinner0db176f2012-04-16 00:16:30 +0200933mappingproxy_str(mappingproxyobject *pp)
Tim Peters6d6c1a32001-08-02 04:15:00 +0000934{
Victor Stinner0db176f2012-04-16 00:16:30 +0200935 return PyObject_Str(pp->mapping);
Tim Peters6d6c1a32001-08-02 04:15:00 +0000936}
937
Ezio Melottiac53ab62010-12-18 14:59:43 +0000938static PyObject *
Victor Stinner0db176f2012-04-16 00:16:30 +0200939mappingproxy_repr(mappingproxyobject *pp)
Ezio Melottiac53ab62010-12-18 14:59:43 +0000940{
Victor Stinner0db176f2012-04-16 00:16:30 +0200941 return PyUnicode_FromFormat("mappingproxy(%R)", pp->mapping);
Ezio Melottiac53ab62010-12-18 14:59:43 +0000942}
943
Guido van Rossum048eb752001-10-02 21:24:57 +0000944static int
Victor Stinner0db176f2012-04-16 00:16:30 +0200945mappingproxy_traverse(PyObject *self, visitproc visit, void *arg)
Guido van Rossum048eb752001-10-02 21:24:57 +0000946{
Victor Stinner0db176f2012-04-16 00:16:30 +0200947 mappingproxyobject *pp = (mappingproxyobject *)self;
948 Py_VISIT(pp->mapping);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000949 return 0;
Guido van Rossum048eb752001-10-02 21:24:57 +0000950}
951
Raymond Hettinger29a6d442002-08-31 15:51:04 +0000952static PyObject *
Victor Stinner0db176f2012-04-16 00:16:30 +0200953mappingproxy_richcompare(mappingproxyobject *v, PyObject *w, int op)
Raymond Hettinger29a6d442002-08-31 15:51:04 +0000954{
Victor Stinner0db176f2012-04-16 00:16:30 +0200955 return PyObject_RichCompare(v->mapping, w, op);
956}
957
958static int
959mappingproxy_check_mapping(PyObject *mapping)
960{
961 if (!PyMapping_Check(mapping)
962 || PyList_Check(mapping)
963 || PyTuple_Check(mapping)) {
964 PyErr_Format(PyExc_TypeError,
965 "mappingproxy() argument must be a mapping, not %s",
966 Py_TYPE(mapping)->tp_name);
967 return -1;
968 }
969 return 0;
970}
971
Serhiy Storchaka18b250f2017-03-19 08:51:07 +0200972/*[clinic input]
973@classmethod
974mappingproxy.__new__ as mappingproxy_new
Victor Stinner0db176f2012-04-16 00:16:30 +0200975
Serhiy Storchaka18b250f2017-03-19 08:51:07 +0200976 mapping: object
977
978[clinic start generated code]*/
979
980static PyObject *
981mappingproxy_new_impl(PyTypeObject *type, PyObject *mapping)
982/*[clinic end generated code: output=65f27f02d5b68fa7 input=d2d620d4f598d4f8]*/
983{
984 mappingproxyobject *mappingproxy;
Victor Stinner0db176f2012-04-16 00:16:30 +0200985
986 if (mappingproxy_check_mapping(mapping) == -1)
987 return NULL;
988
989 mappingproxy = PyObject_GC_New(mappingproxyobject, &PyDictProxy_Type);
990 if (mappingproxy == NULL)
991 return NULL;
992 Py_INCREF(mapping);
993 mappingproxy->mapping = mapping;
994 _PyObject_GC_TRACK(mappingproxy);
995 return (PyObject *)mappingproxy;
Raymond Hettinger29a6d442002-08-31 15:51:04 +0000996}
997
Tim Peters6d6c1a32001-08-02 04:15:00 +0000998PyObject *
Victor Stinner0db176f2012-04-16 00:16:30 +0200999PyDictProxy_New(PyObject *mapping)
Tim Peters6d6c1a32001-08-02 04:15:00 +00001000{
Victor Stinner0db176f2012-04-16 00:16:30 +02001001 mappingproxyobject *pp;
Tim Peters6d6c1a32001-08-02 04:15:00 +00001002
Victor Stinner0db176f2012-04-16 00:16:30 +02001003 if (mappingproxy_check_mapping(mapping) == -1)
1004 return NULL;
1005
1006 pp = PyObject_GC_New(mappingproxyobject, &PyDictProxy_Type);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001007 if (pp != NULL) {
Victor Stinner0db176f2012-04-16 00:16:30 +02001008 Py_INCREF(mapping);
1009 pp->mapping = mapping;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001010 _PyObject_GC_TRACK(pp);
1011 }
1012 return (PyObject *)pp;
Tim Peters6d6c1a32001-08-02 04:15:00 +00001013}
1014
1015
1016/* --- Wrapper object for "slot" methods --- */
1017
1018/* This has no reason to be in this file except that adding new files is a
1019 bit of a pain */
1020
1021typedef struct {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001022 PyObject_HEAD
1023 PyWrapperDescrObject *descr;
1024 PyObject *self;
Tim Peters6d6c1a32001-08-02 04:15:00 +00001025} wrapperobject;
1026
Benjamin Petersoneff61f62011-09-01 16:32:31 -04001027#define Wrapper_Check(v) (Py_TYPE(v) == &_PyMethodWrapper_Type)
Mark Dickinson211c6252009-02-01 10:28:51 +00001028
Tim Peters6d6c1a32001-08-02 04:15:00 +00001029static void
1030wrapper_dealloc(wrapperobject *wp)
1031{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001032 PyObject_GC_UnTrack(wp);
Jeroen Demeyer351c6742019-05-10 19:21:11 +02001033 Py_TRASHCAN_BEGIN(wp, wrapper_dealloc)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001034 Py_XDECREF(wp->descr);
1035 Py_XDECREF(wp->self);
1036 PyObject_GC_Del(wp);
Jeroen Demeyer351c6742019-05-10 19:21:11 +02001037 Py_TRASHCAN_END
Tim Peters6d6c1a32001-08-02 04:15:00 +00001038}
1039
Mark Dickinson211c6252009-02-01 10:28:51 +00001040static PyObject *
1041wrapper_richcompare(PyObject *a, PyObject *b, int op)
Armin Rigoc6686b72005-11-07 08:38:00 +00001042{
Serhiy Storchakaac20e0f2018-07-31 09:18:24 +03001043 wrapperobject *wa, *wb;
1044 int eq;
Mark Dickinson211c6252009-02-01 10:28:51 +00001045
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001046 assert(a != NULL && b != NULL);
Mark Dickinson211c6252009-02-01 10:28:51 +00001047
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001048 /* both arguments should be wrapperobjects */
Serhiy Storchakaac20e0f2018-07-31 09:18:24 +03001049 if ((op != Py_EQ && op != Py_NE)
1050 || !Wrapper_Check(a) || !Wrapper_Check(b))
1051 {
stratakise8b19652017-11-02 11:32:54 +01001052 Py_RETURN_NOTIMPLEMENTED;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001053 }
Mark Dickinson211c6252009-02-01 10:28:51 +00001054
Serhiy Storchakaac20e0f2018-07-31 09:18:24 +03001055 wa = (wrapperobject *)a;
1056 wb = (wrapperobject *)b;
1057 eq = (wa->descr == wb->descr && wa->self == wb->self);
1058 if (eq == (op == Py_EQ)) {
1059 Py_RETURN_TRUE;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001060 }
Serhiy Storchakaac20e0f2018-07-31 09:18:24 +03001061 else {
1062 Py_RETURN_FALSE;
1063 }
Armin Rigoc6686b72005-11-07 08:38:00 +00001064}
1065
Benjamin Peterson8f67d082010-10-17 20:54:53 +00001066static Py_hash_t
Thomas Wouters73e5a5b2006-06-08 15:35:45 +00001067wrapper_hash(wrapperobject *wp)
1068{
Benjamin Peterson8f67d082010-10-17 20:54:53 +00001069 Py_hash_t x, y;
Serhiy Storchakaac20e0f2018-07-31 09:18:24 +03001070 x = _Py_HashPointer(wp->self);
1071 y = _Py_HashPointer(wp->descr);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001072 x = x ^ y;
1073 if (x == -1)
1074 x = -2;
1075 return x;
Thomas Wouters73e5a5b2006-06-08 15:35:45 +00001076}
1077
Armin Rigoc6686b72005-11-07 08:38:00 +00001078static PyObject *
1079wrapper_repr(wrapperobject *wp)
1080{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001081 return PyUnicode_FromFormat("<method-wrapper '%s' of %s object at %p>",
1082 wp->descr->d_base->name,
1083 wp->self->ob_type->tp_name,
1084 wp->self);
Armin Rigoc6686b72005-11-07 08:38:00 +00001085}
1086
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +01001087static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05301088wrapper_reduce(wrapperobject *wp, PyObject *Py_UNUSED(ignored))
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +01001089{
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +01001090 _Py_IDENTIFIER(getattr);
Serhiy Storchakabb86bf42018-12-11 08:28:18 +02001091 return Py_BuildValue("N(OO)", _PyEval_GetBuiltinId(&PyId_getattr),
1092 wp->self, PyDescr_NAME(wp->descr));
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +01001093}
1094
1095static PyMethodDef wrapper_methods[] = {
1096 {"__reduce__", (PyCFunction)wrapper_reduce, METH_NOARGS, NULL},
1097 {NULL, NULL}
1098};
1099
Armin Rigoc6686b72005-11-07 08:38:00 +00001100static PyMemberDef wrapper_members[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001101 {"__self__", T_OBJECT, offsetof(wrapperobject, self), READONLY},
1102 {0}
Tim Peters6d6c1a32001-08-02 04:15:00 +00001103};
1104
1105static PyObject *
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +02001106wrapper_objclass(wrapperobject *wp, void *Py_UNUSED(ignored))
Armin Rigoc6686b72005-11-07 08:38:00 +00001107{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001108 PyObject *c = (PyObject *)PyDescr_TYPE(wp->descr);
Armin Rigoc6686b72005-11-07 08:38:00 +00001109
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001110 Py_INCREF(c);
1111 return c;
Armin Rigoc6686b72005-11-07 08:38:00 +00001112}
1113
1114static PyObject *
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +02001115wrapper_name(wrapperobject *wp, void *Py_UNUSED(ignored))
Tim Peters6d6c1a32001-08-02 04:15:00 +00001116{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001117 const char *s = wp->descr->d_base->name;
Tim Peters6d6c1a32001-08-02 04:15:00 +00001118
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001119 return PyUnicode_FromString(s);
Tim Peters6d6c1a32001-08-02 04:15:00 +00001120}
1121
1122static PyObject *
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +02001123wrapper_doc(wrapperobject *wp, void *Py_UNUSED(ignored))
Tim Peters6d6c1a32001-08-02 04:15:00 +00001124{
Larry Hastings2623c8c2014-02-08 22:15:29 -08001125 return _PyType_GetDocFromInternalDoc(wp->descr->d_base->name, wp->descr->d_base->doc);
Larry Hastings5c661892014-01-24 06:17:25 -08001126}
Tim Peters6d6c1a32001-08-02 04:15:00 +00001127
Larry Hastings5c661892014-01-24 06:17:25 -08001128static PyObject *
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +02001129wrapper_text_signature(wrapperobject *wp, void *Py_UNUSED(ignored))
Larry Hastings5c661892014-01-24 06:17:25 -08001130{
Larry Hastings2623c8c2014-02-08 22:15:29 -08001131 return _PyType_GetTextSignatureFromInternalDoc(wp->descr->d_base->name, wp->descr->d_base->doc);
Tim Peters6d6c1a32001-08-02 04:15:00 +00001132}
1133
Antoine Pitrou9d574812011-12-12 13:47:25 +01001134static PyObject *
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +02001135wrapper_qualname(wrapperobject *wp, void *Py_UNUSED(ignored))
Antoine Pitrou9d574812011-12-12 13:47:25 +01001136{
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +02001137 return descr_get_qualname((PyDescrObject *)wp->descr, NULL);
Antoine Pitrou9d574812011-12-12 13:47:25 +01001138}
1139
Guido van Rossum32d34c82001-09-20 21:45:26 +00001140static PyGetSetDef wrapper_getsets[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001141 {"__objclass__", (getter)wrapper_objclass},
1142 {"__name__", (getter)wrapper_name},
Antoine Pitrou9d574812011-12-12 13:47:25 +01001143 {"__qualname__", (getter)wrapper_qualname},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001144 {"__doc__", (getter)wrapper_doc},
Larry Hastings5c661892014-01-24 06:17:25 -08001145 {"__text_signature__", (getter)wrapper_text_signature},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001146 {0}
Tim Peters6d6c1a32001-08-02 04:15:00 +00001147};
1148
1149static PyObject *
1150wrapper_call(wrapperobject *wp, PyObject *args, PyObject *kwds)
1151{
Serhiy Storchaka5e02c782017-09-21 14:25:36 +03001152 return wrapperdescr_raw_call(wp->descr, wp->self, args, kwds);
Tim Peters6d6c1a32001-08-02 04:15:00 +00001153}
1154
Guido van Rossum048eb752001-10-02 21:24:57 +00001155static int
1156wrapper_traverse(PyObject *self, visitproc visit, void *arg)
1157{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001158 wrapperobject *wp = (wrapperobject *)self;
1159 Py_VISIT(wp->descr);
1160 Py_VISIT(wp->self);
1161 return 0;
Guido van Rossum048eb752001-10-02 21:24:57 +00001162}
1163
Benjamin Petersoneff61f62011-09-01 16:32:31 -04001164PyTypeObject _PyMethodWrapper_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001165 PyVarObject_HEAD_INIT(&PyType_Type, 0)
1166 "method-wrapper", /* tp_name */
1167 sizeof(wrapperobject), /* tp_basicsize */
1168 0, /* tp_itemsize */
1169 /* methods */
1170 (destructor)wrapper_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02001171 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001172 0, /* tp_getattr */
1173 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02001174 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001175 (reprfunc)wrapper_repr, /* tp_repr */
1176 0, /* tp_as_number */
1177 0, /* tp_as_sequence */
1178 0, /* tp_as_mapping */
1179 (hashfunc)wrapper_hash, /* tp_hash */
1180 (ternaryfunc)wrapper_call, /* tp_call */
1181 0, /* tp_str */
1182 PyObject_GenericGetAttr, /* tp_getattro */
1183 0, /* tp_setattro */
1184 0, /* tp_as_buffer */
1185 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /* tp_flags */
1186 0, /* tp_doc */
1187 wrapper_traverse, /* tp_traverse */
1188 0, /* tp_clear */
1189 wrapper_richcompare, /* tp_richcompare */
1190 0, /* tp_weaklistoffset */
1191 0, /* tp_iter */
1192 0, /* tp_iternext */
Antoine Pitrouc9dc4a22013-11-23 18:59:12 +01001193 wrapper_methods, /* tp_methods */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001194 wrapper_members, /* tp_members */
1195 wrapper_getsets, /* tp_getset */
1196 0, /* tp_base */
1197 0, /* tp_dict */
1198 0, /* tp_descr_get */
1199 0, /* tp_descr_set */
Tim Peters6d6c1a32001-08-02 04:15:00 +00001200};
1201
1202PyObject *
1203PyWrapper_New(PyObject *d, PyObject *self)
1204{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001205 wrapperobject *wp;
1206 PyWrapperDescrObject *descr;
Tim Peters6d6c1a32001-08-02 04:15:00 +00001207
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001208 assert(PyObject_TypeCheck(d, &PyWrapperDescr_Type));
1209 descr = (PyWrapperDescrObject *)d;
Victor Stinner3249dec2011-05-01 23:19:15 +02001210 assert(_PyObject_RealIsSubclass((PyObject *)Py_TYPE(self),
Victor Stinnerd9561312011-05-01 23:31:36 +02001211 (PyObject *)PyDescr_TYPE(descr)));
Tim Peters6d6c1a32001-08-02 04:15:00 +00001212
Benjamin Petersoneff61f62011-09-01 16:32:31 -04001213 wp = PyObject_GC_New(wrapperobject, &_PyMethodWrapper_Type);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001214 if (wp != NULL) {
1215 Py_INCREF(descr);
1216 wp->descr = descr;
1217 Py_INCREF(self);
1218 wp->self = self;
1219 _PyObject_GC_TRACK(wp);
1220 }
1221 return (PyObject *)wp;
Tim Peters6d6c1a32001-08-02 04:15:00 +00001222}
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001223
1224
Guido van Rossum8bce4ac2001-09-06 21:56:42 +00001225/* A built-in 'property' type */
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001226
1227/*
Serhiy Storchakad741a882015-06-11 00:06:39 +03001228class property(object):
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001229
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001230 def __init__(self, fget=None, fset=None, fdel=None, doc=None):
1231 if doc is None and fget is not None and hasattr(fget, "__doc__"):
Serhiy Storchakad741a882015-06-11 00:06:39 +03001232 doc = fget.__doc__
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001233 self.__get = fget
1234 self.__set = fset
1235 self.__del = fdel
1236 self.__doc__ = doc
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001237
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001238 def __get__(self, inst, type=None):
1239 if inst is None:
Serhiy Storchakad741a882015-06-11 00:06:39 +03001240 return self
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001241 if self.__get is None:
Serhiy Storchakad741a882015-06-11 00:06:39 +03001242 raise AttributeError, "unreadable attribute"
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001243 return self.__get(inst)
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001244
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001245 def __set__(self, inst, value):
1246 if self.__set is None:
Serhiy Storchakad741a882015-06-11 00:06:39 +03001247 raise AttributeError, "can't set attribute"
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001248 return self.__set(inst, value)
Guido van Rossumba2485f2001-12-10 18:03:34 +00001249
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001250 def __delete__(self, inst):
1251 if self.__del is None:
Serhiy Storchakad741a882015-06-11 00:06:39 +03001252 raise AttributeError, "can't delete attribute"
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001253 return self.__del(inst)
Guido van Rossumba2485f2001-12-10 18:03:34 +00001254
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001255*/
1256
1257typedef struct {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001258 PyObject_HEAD
1259 PyObject *prop_get;
1260 PyObject *prop_set;
1261 PyObject *prop_del;
1262 PyObject *prop_doc;
1263 int getter_doc;
Guido van Rossum8bce4ac2001-09-06 21:56:42 +00001264} propertyobject;
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001265
Christian Heimes0449f632007-12-15 01:27:15 +00001266static PyObject * property_copy(PyObject *, PyObject *, PyObject *,
Benjamin Peterson93964832010-06-28 03:07:10 +00001267 PyObject *);
Christian Heimes0449f632007-12-15 01:27:15 +00001268
Tim Peters66c1a522001-09-24 21:17:50 +00001269static PyMemberDef property_members[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001270 {"fget", T_OBJECT, offsetof(propertyobject, prop_get), READONLY},
1271 {"fset", T_OBJECT, offsetof(propertyobject, prop_set), READONLY},
1272 {"fdel", T_OBJECT, offsetof(propertyobject, prop_del), READONLY},
Raymond Hettingereac503a2015-05-13 01:09:59 -07001273 {"__doc__", T_OBJECT, offsetof(propertyobject, prop_doc), 0},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001274 {0}
Tim Peters66c1a522001-09-24 21:17:50 +00001275};
1276
Christian Heimes0449f632007-12-15 01:27:15 +00001277
Guido van Rossum58da9312007-11-10 23:39:45 +00001278PyDoc_STRVAR(getter_doc,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001279 "Descriptor to change the getter on a property.");
Guido van Rossum58da9312007-11-10 23:39:45 +00001280
Neal Norwitz32dde222008-04-15 06:43:13 +00001281static PyObject *
Guido van Rossum58da9312007-11-10 23:39:45 +00001282property_getter(PyObject *self, PyObject *getter)
1283{
Benjamin Peterson93964832010-06-28 03:07:10 +00001284 return property_copy(self, getter, NULL, NULL);
Guido van Rossum58da9312007-11-10 23:39:45 +00001285}
1286
Christian Heimes0449f632007-12-15 01:27:15 +00001287
Guido van Rossum58da9312007-11-10 23:39:45 +00001288PyDoc_STRVAR(setter_doc,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001289 "Descriptor to change the setter on a property.");
Guido van Rossum58da9312007-11-10 23:39:45 +00001290
Neal Norwitz32dde222008-04-15 06:43:13 +00001291static PyObject *
Guido van Rossum58da9312007-11-10 23:39:45 +00001292property_setter(PyObject *self, PyObject *setter)
1293{
Benjamin Peterson93964832010-06-28 03:07:10 +00001294 return property_copy(self, NULL, setter, NULL);
Guido van Rossum58da9312007-11-10 23:39:45 +00001295}
1296
Christian Heimes0449f632007-12-15 01:27:15 +00001297
Guido van Rossum58da9312007-11-10 23:39:45 +00001298PyDoc_STRVAR(deleter_doc,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001299 "Descriptor to change the deleter on a property.");
Guido van Rossum58da9312007-11-10 23:39:45 +00001300
Neal Norwitz32dde222008-04-15 06:43:13 +00001301static PyObject *
Guido van Rossum58da9312007-11-10 23:39:45 +00001302property_deleter(PyObject *self, PyObject *deleter)
1303{
Benjamin Peterson93964832010-06-28 03:07:10 +00001304 return property_copy(self, NULL, NULL, deleter);
Guido van Rossum58da9312007-11-10 23:39:45 +00001305}
1306
1307
Guido van Rossum58da9312007-11-10 23:39:45 +00001308static PyMethodDef property_methods[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001309 {"getter", property_getter, METH_O, getter_doc},
1310 {"setter", property_setter, METH_O, setter_doc},
1311 {"deleter", property_deleter, METH_O, deleter_doc},
1312 {0}
Guido van Rossum58da9312007-11-10 23:39:45 +00001313};
1314
Tim Peters66c1a522001-09-24 21:17:50 +00001315
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001316static void
Guido van Rossum8bce4ac2001-09-06 21:56:42 +00001317property_dealloc(PyObject *self)
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001318{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001319 propertyobject *gs = (propertyobject *)self;
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001320
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001321 _PyObject_GC_UNTRACK(self);
1322 Py_XDECREF(gs->prop_get);
1323 Py_XDECREF(gs->prop_set);
1324 Py_XDECREF(gs->prop_del);
1325 Py_XDECREF(gs->prop_doc);
1326 self->ob_type->tp_free(self);
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001327}
1328
1329static PyObject *
Guido van Rossum8bce4ac2001-09-06 21:56:42 +00001330property_descr_get(PyObject *self, PyObject *obj, PyObject *type)
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001331{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001332 if (obj == NULL || obj == Py_None) {
1333 Py_INCREF(self);
1334 return self;
1335 }
Victor Stinnere972c132018-10-01 03:03:22 -07001336
1337 propertyobject *gs = (propertyobject *)self;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001338 if (gs->prop_get == NULL) {
1339 PyErr_SetString(PyExc_AttributeError, "unreadable attribute");
1340 return NULL;
1341 }
Victor Stinnere972c132018-10-01 03:03:22 -07001342
Jeroen Demeyer196a5302019-07-04 12:31:34 +02001343 return _PyObject_CallOneArg(gs->prop_get, obj);
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001344}
1345
1346static int
Guido van Rossum8bce4ac2001-09-06 21:56:42 +00001347property_descr_set(PyObject *self, PyObject *obj, PyObject *value)
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001348{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001349 propertyobject *gs = (propertyobject *)self;
1350 PyObject *func, *res;
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001351
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001352 if (value == NULL)
1353 func = gs->prop_del;
1354 else
1355 func = gs->prop_set;
1356 if (func == NULL) {
1357 PyErr_SetString(PyExc_AttributeError,
1358 value == NULL ?
1359 "can't delete attribute" :
1360 "can't set attribute");
1361 return -1;
1362 }
1363 if (value == NULL)
Jeroen Demeyer196a5302019-07-04 12:31:34 +02001364 res = _PyObject_CallOneArg(func, obj);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001365 else
Benjamin Peterson9b955de2010-12-07 04:04:02 +00001366 res = PyObject_CallFunctionObjArgs(func, obj, value, NULL);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001367 if (res == NULL)
1368 return -1;
1369 Py_DECREF(res);
1370 return 0;
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001371}
1372
Christian Heimes0449f632007-12-15 01:27:15 +00001373static PyObject *
Benjamin Peterson93964832010-06-28 03:07:10 +00001374property_copy(PyObject *old, PyObject *get, PyObject *set, PyObject *del)
Christian Heimes0449f632007-12-15 01:27:15 +00001375{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001376 propertyobject *pold = (propertyobject *)old;
Benjamin Peterson93964832010-06-28 03:07:10 +00001377 PyObject *new, *type, *doc;
Christian Heimes0449f632007-12-15 01:27:15 +00001378
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001379 type = PyObject_Type(old);
1380 if (type == NULL)
1381 return NULL;
Christian Heimes0449f632007-12-15 01:27:15 +00001382
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001383 if (get == NULL || get == Py_None) {
1384 Py_XDECREF(get);
1385 get = pold->prop_get ? pold->prop_get : Py_None;
1386 }
1387 if (set == NULL || set == Py_None) {
1388 Py_XDECREF(set);
1389 set = pold->prop_set ? pold->prop_set : Py_None;
1390 }
1391 if (del == NULL || del == Py_None) {
1392 Py_XDECREF(del);
1393 del = pold->prop_del ? pold->prop_del : Py_None;
1394 }
Benjamin Peterson93964832010-06-28 03:07:10 +00001395 if (pold->getter_doc && get != Py_None) {
1396 /* make _init use __doc__ from getter */
1397 doc = Py_None;
1398 }
1399 else {
1400 doc = pold->prop_doc ? pold->prop_doc : Py_None;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001401 }
R. David Murrayb18500d2009-05-04 22:59:07 +00001402
Victor Stinner5abaa2b2016-12-09 16:22:32 +01001403 new = PyObject_CallFunctionObjArgs(type, get, set, del, doc, NULL);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001404 Py_DECREF(type);
1405 if (new == NULL)
1406 return NULL;
1407 return new;
Christian Heimes0449f632007-12-15 01:27:15 +00001408}
1409
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001410/*[clinic input]
1411property.__init__ as property_init
1412
1413 fget: object(c_default="NULL") = None
1414 function to be used for getting an attribute value
1415 fset: object(c_default="NULL") = None
1416 function to be used for setting an attribute value
1417 fdel: object(c_default="NULL") = None
1418 function to be used for del'ing an attribute
1419 doc: object(c_default="NULL") = None
1420 docstring
1421
1422Property attribute.
1423
1424Typical use is to define a managed attribute x:
1425
1426class C(object):
1427 def getx(self): return self._x
1428 def setx(self, value): self._x = value
1429 def delx(self): del self._x
1430 x = property(getx, setx, delx, "I'm the 'x' property.")
1431
1432Decorators make defining new properties or modifying existing ones easy:
1433
1434class C(object):
1435 @property
1436 def x(self):
1437 "I am the 'x' property."
1438 return self._x
1439 @x.setter
1440 def x(self, value):
1441 self._x = value
1442 @x.deleter
1443 def x(self):
1444 del self._x
1445[clinic start generated code]*/
1446
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001447static int
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001448property_init_impl(propertyobject *self, PyObject *fget, PyObject *fset,
1449 PyObject *fdel, PyObject *doc)
1450/*[clinic end generated code: output=01a960742b692b57 input=dfb5dbbffc6932d5]*/
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001451{
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001452 if (fget == Py_None)
1453 fget = NULL;
1454 if (fset == Py_None)
1455 fset = NULL;
1456 if (fdel == Py_None)
1457 fdel = NULL;
Tim Peters66c1a522001-09-24 21:17:50 +00001458
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001459 Py_XINCREF(fget);
1460 Py_XINCREF(fset);
1461 Py_XINCREF(fdel);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001462 Py_XINCREF(doc);
Christian Heimes0449f632007-12-15 01:27:15 +00001463
Oren Milmand019bc82018-02-13 12:28:33 +02001464 Py_XSETREF(self->prop_get, fget);
1465 Py_XSETREF(self->prop_set, fset);
1466 Py_XSETREF(self->prop_del, fdel);
1467 Py_XSETREF(self->prop_doc, doc);
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001468 self->getter_doc = 0;
Thomas Wouters0e3f5912006-08-11 14:57:12 +00001469
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001470 /* if no docstring given and the getter has one, use that one */
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001471 if ((doc == NULL || doc == Py_None) && fget != NULL) {
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02001472 _Py_IDENTIFIER(__doc__);
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001473 PyObject *get_doc = _PyObject_GetAttrId(fget, &PyId___doc__);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001474 if (get_doc) {
1475 if (Py_TYPE(self) == &PyProperty_Type) {
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001476 Py_XSETREF(self->prop_doc, get_doc);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001477 }
1478 else {
1479 /* If this is a property subclass, put __doc__
1480 in dict of the subclass instance instead,
1481 otherwise it gets shadowed by __doc__ in the
1482 class's dict. */
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001483 int err = _PyObject_SetAttrId((PyObject *)self, &PyId___doc__, get_doc);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001484 Py_DECREF(get_doc);
1485 if (err < 0)
1486 return -1;
1487 }
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001488 self->getter_doc = 1;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001489 }
1490 else if (PyErr_ExceptionMatches(PyExc_Exception)) {
1491 PyErr_Clear();
1492 }
1493 else {
1494 return -1;
1495 }
1496 }
1497
1498 return 0;
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001499}
1500
Benjamin Petersonbfebb7b2011-12-15 15:34:02 -05001501static PyObject *
1502property_get___isabstractmethod__(propertyobject *prop, void *closure)
1503{
1504 int res = _PyObject_IsAbstract(prop->prop_get);
1505 if (res == -1) {
1506 return NULL;
1507 }
1508 else if (res) {
1509 Py_RETURN_TRUE;
1510 }
1511
1512 res = _PyObject_IsAbstract(prop->prop_set);
1513 if (res == -1) {
1514 return NULL;
1515 }
1516 else if (res) {
1517 Py_RETURN_TRUE;
1518 }
1519
1520 res = _PyObject_IsAbstract(prop->prop_del);
1521 if (res == -1) {
1522 return NULL;
1523 }
1524 else if (res) {
1525 Py_RETURN_TRUE;
1526 }
1527 Py_RETURN_FALSE;
1528}
1529
1530static PyGetSetDef property_getsetlist[] = {
1531 {"__isabstractmethod__",
1532 (getter)property_get___isabstractmethod__, NULL,
1533 NULL,
1534 NULL},
1535 {NULL} /* Sentinel */
1536};
1537
Guido van Rossum048eb752001-10-02 21:24:57 +00001538static int
1539property_traverse(PyObject *self, visitproc visit, void *arg)
1540{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001541 propertyobject *pp = (propertyobject *)self;
1542 Py_VISIT(pp->prop_get);
1543 Py_VISIT(pp->prop_set);
1544 Py_VISIT(pp->prop_del);
1545 Py_VISIT(pp->prop_doc);
1546 return 0;
Guido van Rossum048eb752001-10-02 21:24:57 +00001547}
1548
Raymond Hettingerd4be6912015-05-13 11:12:33 -07001549static int
1550property_clear(PyObject *self)
1551{
1552 propertyobject *pp = (propertyobject *)self;
1553 Py_CLEAR(pp->prop_doc);
1554 return 0;
1555}
1556
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001557#include "clinic/descrobject.c.h"
1558
1559PyTypeObject PyDictProxy_Type = {
1560 PyVarObject_HEAD_INIT(&PyType_Type, 0)
1561 "mappingproxy", /* tp_name */
1562 sizeof(mappingproxyobject), /* tp_basicsize */
1563 0, /* tp_itemsize */
1564 /* methods */
1565 (destructor)mappingproxy_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02001566 0, /* tp_vectorcall_offset */
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001567 0, /* tp_getattr */
1568 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02001569 0, /* tp_as_async */
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001570 (reprfunc)mappingproxy_repr, /* tp_repr */
1571 0, /* tp_as_number */
1572 &mappingproxy_as_sequence, /* tp_as_sequence */
1573 &mappingproxy_as_mapping, /* tp_as_mapping */
1574 0, /* tp_hash */
1575 0, /* tp_call */
1576 (reprfunc)mappingproxy_str, /* tp_str */
1577 PyObject_GenericGetAttr, /* tp_getattro */
1578 0, /* tp_setattro */
1579 0, /* tp_as_buffer */
1580 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /* tp_flags */
1581 0, /* tp_doc */
1582 mappingproxy_traverse, /* tp_traverse */
1583 0, /* tp_clear */
1584 (richcmpfunc)mappingproxy_richcompare, /* tp_richcompare */
1585 0, /* tp_weaklistoffset */
1586 (getiterfunc)mappingproxy_getiter, /* tp_iter */
1587 0, /* tp_iternext */
1588 mappingproxy_methods, /* tp_methods */
1589 0, /* tp_members */
1590 0, /* tp_getset */
1591 0, /* tp_base */
1592 0, /* tp_dict */
1593 0, /* tp_descr_get */
1594 0, /* tp_descr_set */
1595 0, /* tp_dictoffset */
1596 0, /* tp_init */
1597 0, /* tp_alloc */
1598 mappingproxy_new, /* tp_new */
1599};
1600
Guido van Rossum8bce4ac2001-09-06 21:56:42 +00001601PyTypeObject PyProperty_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001602 PyVarObject_HEAD_INIT(&PyType_Type, 0)
1603 "property", /* tp_name */
1604 sizeof(propertyobject), /* tp_basicsize */
1605 0, /* tp_itemsize */
1606 /* methods */
1607 property_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02001608 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001609 0, /* tp_getattr */
1610 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02001611 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001612 0, /* tp_repr */
1613 0, /* tp_as_number */
1614 0, /* tp_as_sequence */
1615 0, /* tp_as_mapping */
1616 0, /* tp_hash */
1617 0, /* tp_call */
1618 0, /* tp_str */
1619 PyObject_GenericGetAttr, /* tp_getattro */
1620 0, /* tp_setattro */
1621 0, /* tp_as_buffer */
1622 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC |
1623 Py_TPFLAGS_BASETYPE, /* tp_flags */
Serhiy Storchaka18b250f2017-03-19 08:51:07 +02001624 property_init__doc__, /* tp_doc */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001625 property_traverse, /* tp_traverse */
Raymond Hettingerd4be6912015-05-13 11:12:33 -07001626 (inquiry)property_clear, /* tp_clear */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001627 0, /* tp_richcompare */
1628 0, /* tp_weaklistoffset */
1629 0, /* tp_iter */
1630 0, /* tp_iternext */
1631 property_methods, /* tp_methods */
1632 property_members, /* tp_members */
Benjamin Petersonbfebb7b2011-12-15 15:34:02 -05001633 property_getsetlist, /* tp_getset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001634 0, /* tp_base */
1635 0, /* tp_dict */
1636 property_descr_get, /* tp_descr_get */
1637 property_descr_set, /* tp_descr_set */
1638 0, /* tp_dictoffset */
1639 property_init, /* tp_init */
1640 PyType_GenericAlloc, /* tp_alloc */
1641 PyType_GenericNew, /* tp_new */
1642 PyObject_GC_Del, /* tp_free */
Guido van Rossum29a62dd2001-08-23 21:40:38 +00001643};