Line | Count | Source (jump to first uncovered line) |
1 | |
2 | /* Function object implementation */ |
3 | |
4 | #include "Python.h" |
5 | #include "pycore_ceval.h" // _PyEval_BuiltinsFromGlobals() |
6 | #include "pycore_object.h" // _PyObject_GC_UNTRACK() |
7 | #include "pycore_pyerrors.h" // _PyErr_Occurred() |
8 | #include "structmember.h" // PyMemberDef |
9 | |
10 | static uint32_t next_func_version = 1; |
11 | |
12 | PyFunctionObject * |
13 | _PyFunction_FromConstructor(PyFrameConstructor *constr) |
14 | { |
15 | |
16 | PyFunctionObject *op = PyObject_GC_New(PyFunctionObject, &PyFunction_Type); |
17 | if (op == NULL) { Branch (17:9): [True: 0, False: 55.1k]
|
18 | return NULL; |
19 | } |
20 | Py_INCREF(constr->fc_globals); |
21 | op->func_globals = constr->fc_globals; |
22 | Py_INCREF(constr->fc_builtins); |
23 | op->func_builtins = constr->fc_builtins; |
24 | Py_INCREF(constr->fc_name); |
25 | op->func_name = constr->fc_name; |
26 | Py_INCREF(constr->fc_qualname); |
27 | op->func_qualname = constr->fc_qualname; |
28 | Py_INCREF(constr->fc_code); |
29 | op->func_code = constr->fc_code; |
30 | op->func_defaults = NULL; |
31 | op->func_kwdefaults = NULL; |
32 | Py_XINCREF(constr->fc_closure); |
33 | op->func_closure = constr->fc_closure; |
34 | Py_INCREF(Py_None); |
35 | op->func_doc = Py_None; |
36 | op->func_dict = NULL; |
37 | op->func_weakreflist = NULL; |
38 | op->func_module = NULL; |
39 | op->func_annotations = NULL; |
40 | op->vectorcall = _PyFunction_Vectorcall; |
41 | op->func_version = 0; |
42 | _PyObject_GC_TRACK(op); |
43 | return op; |
44 | } |
45 | |
46 | PyObject * |
47 | PyFunction_NewWithQualName(PyObject *code, PyObject *globals, PyObject *qualname) |
48 | { |
49 | assert(globals != NULL); |
50 | assert(PyDict_Check(globals)); |
51 | Py_INCREF(globals); |
52 | |
53 | PyThreadState *tstate = _PyThreadState_GET(); |
54 | |
55 | PyCodeObject *code_obj = (PyCodeObject *)code; |
56 | Py_INCREF(code_obj); |
57 | |
58 | PyObject *name = code_obj->co_name; |
59 | assert(name != NULL); |
60 | Py_INCREF(name); |
61 | |
62 | if (!qualname) { Branch (62:9): [True: 2.52M, False: 0]
|
63 | qualname = code_obj->co_qualname; |
64 | } |
65 | assert(qualname != NULL); |
66 | Py_INCREF(qualname); |
67 | |
68 | PyObject *consts = code_obj->co_consts; |
69 | assert(PyTuple_Check(consts)); |
70 | PyObject *doc; |
71 | if (PyTuple_Size(consts) >= 1) { Branch (71:9): [True: 1.59M, False: 927k]
|
72 | doc = PyTuple_GetItem(consts, 0); |
73 | if (!PyUnicode_Check(doc)) { Branch (73:13): [True: 1.35M, False: 237k]
|
74 | doc = Py_None; |
75 | } |
76 | } |
77 | else { |
78 | doc = Py_None; |
79 | } |
80 | Py_INCREF(doc); |
81 | |
82 | // __module__: Use globals['__name__'] if it exists, or NULL. |
83 | PyObject *module = PyDict_GetItemWithError(globals, &_Py_ID(__name__)); |
84 | PyObject *builtins = NULL; |
85 | if (module == NULL && _PyErr_Occurred(tstate)5.22k ) { Branch (85:9): [True: 5.22k, False: 2.51M]
Branch (85:27): [True: 0, False: 5.22k]
|
86 | goto error; |
87 | } |
88 | Py_XINCREF(module); |
89 | |
90 | builtins = _PyEval_BuiltinsFromGlobals(tstate, globals); // borrowed ref |
91 | if (builtins == NULL) { Branch (91:9): [True: 0, False: 2.52M]
|
92 | goto error; |
93 | } |
94 | Py_INCREF(builtins); |
95 | |
96 | PyFunctionObject *op = PyObject_GC_New(PyFunctionObject, &PyFunction_Type); |
97 | if (op == NULL) { Branch (97:9): [True: 0, False: 2.52M]
|
98 | goto error; |
99 | } |
100 | /* Note: No failures from this point on, since func_dealloc() does not |
101 | expect a partially-created object. */ |
102 | |
103 | op->func_globals = globals; |
104 | op->func_builtins = builtins; |
105 | op->func_name = name; |
106 | op->func_qualname = qualname; |
107 | op->func_code = (PyObject*)code_obj; |
108 | op->func_defaults = NULL; // No default positional arguments |
109 | op->func_kwdefaults = NULL; // No default keyword arguments |
110 | op->func_closure = NULL; |
111 | op->func_doc = doc; |
112 | op->func_dict = NULL; |
113 | op->func_weakreflist = NULL; |
114 | op->func_module = module; |
115 | op->func_annotations = NULL; |
116 | op->vectorcall = _PyFunction_Vectorcall; |
117 | op->func_version = 0; |
118 | _PyObject_GC_TRACK(op); |
119 | return (PyObject *)op; |
120 | |
121 | error: |
122 | Py_DECREF(globals); |
123 | Py_DECREF(code_obj); |
124 | Py_DECREF(name); |
125 | Py_DECREF(qualname); |
126 | Py_DECREF(doc); |
127 | Py_XDECREF(module); |
128 | Py_XDECREF(builtins); |
129 | return NULL; |
130 | } |
131 | |
132 | uint32_t _PyFunction_GetVersionForCurrentState(PyFunctionObject *func) |
133 | { |
134 | if (func->func_version != 0) { Branch (134:9): [True: 90.9k, False: 42.7k]
|
135 | return func->func_version; |
136 | } |
137 | if (next_func_version == 0) { Branch (137:9): [True: 0, False: 42.7k]
|
138 | return 0; |
139 | } |
140 | uint32_t v = next_func_version++; |
141 | func->func_version = v; |
142 | return v; |
143 | } |
144 | |
145 | PyObject * |
146 | PyFunction_New(PyObject *code, PyObject *globals) |
147 | { |
148 | return PyFunction_NewWithQualName(code, globals, NULL); |
149 | } |
150 | |
151 | PyObject * |
152 | PyFunction_GetCode(PyObject *op) |
153 | { |
154 | if (!PyFunction_Check(op)) { Branch (154:9): [True: 0, False: 0]
|
155 | PyErr_BadInternalCall(); |
156 | return NULL; |
157 | } |
158 | return ((PyFunctionObject *) op) -> func_code; |
159 | } |
160 | |
161 | PyObject * |
162 | PyFunction_GetGlobals(PyObject *op) |
163 | { |
164 | if (!PyFunction_Check(op)) { Branch (164:9): [True: 0, False: 0]
|
165 | PyErr_BadInternalCall(); |
166 | return NULL; |
167 | } |
168 | return ((PyFunctionObject *) op) -> func_globals; |
169 | } |
170 | |
171 | PyObject * |
172 | PyFunction_GetModule(PyObject *op) |
173 | { |
174 | if (!PyFunction_Check(op)) { Branch (174:9): [True: 0, False: 0]
|
175 | PyErr_BadInternalCall(); |
176 | return NULL; |
177 | } |
178 | return ((PyFunctionObject *) op) -> func_module; |
179 | } |
180 | |
181 | PyObject * |
182 | PyFunction_GetDefaults(PyObject *op) |
183 | { |
184 | if (!PyFunction_Check(op)) { Branch (184:9): [True: 0, False: 0]
|
185 | PyErr_BadInternalCall(); |
186 | return NULL; |
187 | } |
188 | return ((PyFunctionObject *) op) -> func_defaults; |
189 | } |
190 | |
191 | int |
192 | PyFunction_SetDefaults(PyObject *op, PyObject *defaults) |
193 | { |
194 | if (!PyFunction_Check(op)) { Branch (194:9): [True: 0, False: 0]
|
195 | PyErr_BadInternalCall(); |
196 | return -1; |
197 | } |
198 | if (defaults == Py_None) Branch (198:9): [True: 0, False: 0]
|
199 | defaults = NULL; |
200 | else if (defaults && PyTuple_Check(defaults)) { Branch (200:14): [True: 0, False: 0]
|
201 | Py_INCREF(defaults); |
202 | } |
203 | else { |
204 | PyErr_SetString(PyExc_SystemError, "non-tuple default args"); |
205 | return -1; |
206 | } |
207 | ((PyFunctionObject *)op)->func_version = 0; |
208 | Py_XSETREF(((PyFunctionObject *)op)->func_defaults, defaults); |
209 | return 0; |
210 | } |
211 | |
212 | PyObject * |
213 | PyFunction_GetKwDefaults(PyObject *op) |
214 | { |
215 | if (!PyFunction_Check(op)) { Branch (215:9): [True: 0, False: 0]
|
216 | PyErr_BadInternalCall(); |
217 | return NULL; |
218 | } |
219 | return ((PyFunctionObject *) op) -> func_kwdefaults; |
220 | } |
221 | |
222 | int |
223 | PyFunction_SetKwDefaults(PyObject *op, PyObject *defaults) |
224 | { |
225 | if (!PyFunction_Check(op)) { Branch (225:9): [True: 0, False: 0]
|
226 | PyErr_BadInternalCall(); |
227 | return -1; |
228 | } |
229 | if (defaults == Py_None) Branch (229:9): [True: 0, False: 0]
|
230 | defaults = NULL; |
231 | else if (defaults && PyDict_Check(defaults)) { Branch (231:14): [True: 0, False: 0]
|
232 | Py_INCREF(defaults); |
233 | } |
234 | else { |
235 | PyErr_SetString(PyExc_SystemError, |
236 | "non-dict keyword only default args"); |
237 | return -1; |
238 | } |
239 | ((PyFunctionObject *)op)->func_version = 0; |
240 | Py_XSETREF(((PyFunctionObject *)op)->func_kwdefaults, defaults); |
241 | return 0; |
242 | } |
243 | |
244 | PyObject * |
245 | PyFunction_GetClosure(PyObject *op) |
246 | { |
247 | if (!PyFunction_Check(op)) { Branch (247:9): [True: 0, False: 0]
|
248 | PyErr_BadInternalCall(); |
249 | return NULL; |
250 | } |
251 | return ((PyFunctionObject *) op) -> func_closure; |
252 | } |
253 | |
254 | int |
255 | PyFunction_SetClosure(PyObject *op, PyObject *closure) |
256 | { |
257 | if (!PyFunction_Check(op)) { Branch (257:9): [True: 0, False: 0]
|
258 | PyErr_BadInternalCall(); |
259 | return -1; |
260 | } |
261 | if (closure == Py_None) Branch (261:9): [True: 0, False: 0]
|
262 | closure = NULL; |
263 | else if (PyTuple_Check(closure)) { |
264 | Py_INCREF(closure); |
265 | } |
266 | else { |
267 | PyErr_Format(PyExc_SystemError, |
268 | "expected tuple for closure, got '%.100s'", |
269 | Py_TYPE(closure)->tp_name); |
270 | return -1; |
271 | } |
272 | ((PyFunctionObject *)op)->func_version = 0; |
273 | Py_XSETREF(((PyFunctionObject *)op)->func_closure, closure); |
274 | return 0; |
275 | } |
276 | |
277 | static PyObject * |
278 | func_get_annotation_dict(PyFunctionObject *op) |
279 | { |
280 | if (op->func_annotations == NULL) { Branch (280:9): [True: 0, False: 25.9k]
|
281 | return NULL; |
282 | } |
283 | if (PyTuple_CheckExact(op->func_annotations)) { |
284 | PyObject *ann_tuple = op->func_annotations; |
285 | PyObject *ann_dict = PyDict_New(); |
286 | if (ann_dict == NULL) { Branch (286:13): [True: 0, False: 1.35k]
|
287 | return NULL; |
288 | } |
289 | |
290 | assert(PyTuple_GET_SIZE(ann_tuple) % 2 == 0); |
291 | |
292 | for (Py_ssize_t i = 0; i < PyTuple_GET_SIZE(ann_tuple); i += 22.75k ) { Branch (292:32): [True: 2.75k, False: 1.35k]
|
293 | int err = PyDict_SetItem(ann_dict, |
294 | PyTuple_GET_ITEM(ann_tuple, i), |
295 | PyTuple_GET_ITEM(ann_tuple, i + 1)); |
296 | |
297 | if (err < 0) { Branch (297:17): [True: 0, False: 2.75k]
|
298 | return NULL; |
299 | } |
300 | } |
301 | Py_SETREF(op->func_annotations, ann_dict); |
302 | } |
303 | Py_INCREF(op->func_annotations); |
304 | assert(PyDict_Check(op->func_annotations)); |
305 | return op->func_annotations; |
306 | } |
307 | |
308 | PyObject * |
309 | PyFunction_GetAnnotations(PyObject *op) |
310 | { |
311 | if (!PyFunction_Check(op)) { Branch (311:9): [True: 0, False: 0]
|
312 | PyErr_BadInternalCall(); |
313 | return NULL; |
314 | } |
315 | return func_get_annotation_dict((PyFunctionObject *)op); |
316 | } |
317 | |
318 | int |
319 | PyFunction_SetAnnotations(PyObject *op, PyObject *annotations) |
320 | { |
321 | if (!PyFunction_Check(op)) { Branch (321:9): [True: 0, False: 0]
|
322 | PyErr_BadInternalCall(); |
323 | return -1; |
324 | } |
325 | if (annotations == Py_None) Branch (325:9): [True: 0, False: 0]
|
326 | annotations = NULL; |
327 | else if (annotations && PyDict_Check(annotations)) { Branch (327:14): [True: 0, False: 0]
|
328 | Py_INCREF(annotations); |
329 | } |
330 | else { |
331 | PyErr_SetString(PyExc_SystemError, |
332 | "non-dict annotations"); |
333 | return -1; |
334 | } |
335 | ((PyFunctionObject *)op)->func_version = 0; |
336 | Py_XSETREF(((PyFunctionObject *)op)->func_annotations, annotations); |
337 | return 0; |
338 | } |
339 | |
340 | /* Methods */ |
341 | |
342 | #define OFF(x) offsetof(PyFunctionObject, x) |
343 | |
344 | static PyMemberDef func_memberlist[] = { |
345 | {"__closure__", T_OBJECT, OFF(func_closure), READONLY}, |
346 | {"__doc__", T_OBJECT, OFF(func_doc), 0}, |
347 | {"__globals__", T_OBJECT, OFF(func_globals), READONLY}, |
348 | {"__module__", T_OBJECT, OFF(func_module), 0}, |
349 | {"__builtins__", T_OBJECT, OFF(func_builtins), READONLY}, |
350 | {NULL} /* Sentinel */ |
351 | }; |
352 | |
353 | static PyObject * |
354 | func_get_code(PyFunctionObject *op, void *Py_UNUSED(ignored)) |
355 | { |
356 | if (PySys_Audit("object.__getattr__", "Os", op, "__code__") < 0) { Branch (356:9): [True: 0, False: 19.0k]
|
357 | return NULL; |
358 | } |
359 | |
360 | Py_INCREF(op->func_code); |
361 | return op->func_code; |
362 | } |
363 | |
364 | static int |
365 | func_set_code(PyFunctionObject *op, PyObject *value, void *Py_UNUSED(ignored)) |
366 | { |
367 | Py_ssize_t nclosure; |
368 | int nfree; |
369 | |
370 | /* Not legal to del f.func_code or to set it to anything |
371 | * other than a code object. */ |
372 | if (value == NULL || !PyCode_Check(value)) { Branch (372:9): [True: 0, False: 43]
Branch (372:26): [True: 0, False: 43]
|
373 | PyErr_SetString(PyExc_TypeError, |
374 | "__code__ must be set to a code object"); |
375 | return -1; |
376 | } |
377 | |
378 | if (PySys_Audit("object.__setattr__", "OsO", Branch (378:9): [True: 0, False: 43]
|
379 | op, "__code__", value) < 0) { |
380 | return -1; |
381 | } |
382 | |
383 | nfree = ((PyCodeObject *)value)->co_nfreevars; |
384 | nclosure = (op->func_closure == NULL ? 037 : Branch (384:17): [True: 37, False: 6]
|
385 | PyTuple_GET_SIZE6 (op->func_closure)); |
386 | if (nclosure != nfree) { Branch (386:9): [True: 2, False: 41]
|
387 | PyErr_Format(PyExc_ValueError, |
388 | "%U() requires a code object with %zd free vars," |
389 | " not %zd", |
390 | op->func_name, |
391 | nclosure, nfree); |
392 | return -1; |
393 | } |
394 | op->func_version = 0; |
395 | Py_INCREF(value); |
396 | Py_XSETREF(op->func_code, value); |
397 | return 0; |
398 | } |
399 | |
400 | static PyObject * |
401 | func_get_name(PyFunctionObject *op, void *Py_UNUSED(ignored)) |
402 | { |
403 | Py_INCREF(op->func_name); |
404 | return op->func_name; |
405 | } |
406 | |
407 | static int |
408 | func_set_name(PyFunctionObject *op, PyObject *value, void *Py_UNUSED(ignored)) |
409 | { |
410 | /* Not legal to del f.func_name or to set it to anything |
411 | * other than a string object. */ |
412 | if (value == NULL || !10.4k PyUnicode_Check10.4k (value)) { Branch (412:9): [True: 1, False: 10.4k]
Branch (412:26): [True: 1, False: 10.4k]
|
413 | PyErr_SetString(PyExc_TypeError, |
414 | "__name__ must be set to a string object"); |
415 | return -1; |
416 | } |
417 | Py_INCREF(value); |
418 | Py_XSETREF(op->func_name, value); |
419 | return 0; |
420 | } |
421 | |
422 | static PyObject * |
423 | func_get_qualname(PyFunctionObject *op, void *Py_UNUSED(ignored)) |
424 | { |
425 | Py_INCREF(op->func_qualname); |
426 | return op->func_qualname; |
427 | } |
428 | |
429 | static int |
430 | func_set_qualname(PyFunctionObject *op, PyObject *value, void *Py_UNUSED(ignored)) |
431 | { |
432 | /* Not legal to del f.__qualname__ or to set it to anything |
433 | * other than a string object. */ |
434 | if (value == NULL || !10.2k PyUnicode_Check10.2k (value)) { Branch (434:9): [True: 1, False: 10.2k]
Branch (434:26): [True: 1, False: 10.2k]
|
435 | PyErr_SetString(PyExc_TypeError, |
436 | "__qualname__ must be set to a string object"); |
437 | return -1; |
438 | } |
439 | Py_INCREF(value); |
440 | Py_XSETREF(op->func_qualname, value); |
441 | return 0; |
442 | } |
443 | |
444 | static PyObject * |
445 | func_get_defaults(PyFunctionObject *op, void *Py_UNUSED(ignored)) |
446 | { |
447 | if (PySys_Audit("object.__getattr__", "Os", op, "__defaults__") < 0) { Branch (447:9): [True: 0, False: 3.53k]
|
448 | return NULL; |
449 | } |
450 | if (op->func_defaults == NULL) { Branch (450:9): [True: 2.72k, False: 812]
|
451 | Py_RETURN_NONE; |
452 | } |
453 | Py_INCREF(op->func_defaults); |
454 | return op->func_defaults; |
455 | } |
456 | |
457 | static int |
458 | func_set_defaults(PyFunctionObject *op, PyObject *value, void *Py_UNUSED(ignored)) |
459 | { |
460 | /* Legal to del f.func_defaults. |
461 | * Can only set func_defaults to NULL or a tuple. */ |
462 | if (value == Py_None) Branch (462:9): [True: 253, False: 119]
|
463 | value = NULL; |
464 | if (value != NULL && !116 PyTuple_Check116 (value)) { Branch (464:9): [True: 116, False: 256]
Branch (464:26): [True: 0, False: 116]
|
465 | PyErr_SetString(PyExc_TypeError, |
466 | "__defaults__ must be set to a tuple object"); |
467 | return -1; |
468 | } |
469 | if (value) { Branch (469:9): [True: 116, False: 256]
|
470 | if (PySys_Audit("object.__setattr__", "OsO", Branch (470:13): [True: 0, False: 116]
|
471 | op, "__defaults__", value) < 0) { |
472 | return -1; |
473 | } |
474 | } else if (PySys_Audit("object.__delattr__", "Os", Branch (474:16): [True: 0, False: 256]
|
475 | op, "__defaults__") < 0) { |
476 | return -1; |
477 | } |
478 | |
479 | op->func_version = 0; |
480 | Py_XINCREF(value); |
481 | Py_XSETREF(op->func_defaults, value); |
482 | return 0; |
483 | } |
484 | |
485 | static PyObject * |
486 | func_get_kwdefaults(PyFunctionObject *op, void *Py_UNUSED(ignored)) |
487 | { |
488 | if (PySys_Audit("object.__getattr__", "Os", Branch (488:9): [True: 0, False: 3.41k]
|
489 | op, "__kwdefaults__") < 0) { |
490 | return NULL; |
491 | } |
492 | if (op->func_kwdefaults == NULL) { Branch (492:9): [True: 3.28k, False: 124]
|
493 | Py_RETURN_NONE; |
494 | } |
495 | Py_INCREF(op->func_kwdefaults); |
496 | return op->func_kwdefaults; |
497 | } |
498 | |
499 | static int |
500 | func_set_kwdefaults(PyFunctionObject *op, PyObject *value, void *Py_UNUSED(ignored)) |
501 | { |
502 | if (value == Py_None) Branch (502:9): [True: 292, False: 7]
|
503 | value = NULL; |
504 | /* Legal to del f.func_kwdefaults. |
505 | * Can only set func_kwdefaults to NULL or a dict. */ |
506 | if (value != NULL && !6 PyDict_Check6 (value)) { Branch (506:9): [True: 6, False: 293]
Branch (506:26): [True: 0, False: 6]
|
507 | PyErr_SetString(PyExc_TypeError, |
508 | "__kwdefaults__ must be set to a dict object"); |
509 | return -1; |
510 | } |
511 | if (value) { Branch (511:9): [True: 6, False: 293]
|
512 | if (PySys_Audit("object.__setattr__", "OsO", Branch (512:13): [True: 0, False: 6]
|
513 | op, "__kwdefaults__", value) < 0) { |
514 | return -1; |
515 | } |
516 | } else if (PySys_Audit("object.__delattr__", "Os", Branch (516:16): [True: 0, False: 293]
|
517 | op, "__kwdefaults__") < 0) { |
518 | return -1; |
519 | } |
520 | |
521 | op->func_version = 0; |
522 | Py_XINCREF(value); |
523 | Py_XSETREF(op->func_kwdefaults, value); |
524 | return 0; |
525 | } |
526 | |
527 | static PyObject * |
528 | func_get_annotations(PyFunctionObject *op, void *Py_UNUSED(ignored)) |
529 | { |
530 | if (op->func_annotations == NULL) { Branch (530:9): [True: 22.4k, False: 3.49k]
|
531 | op->func_annotations = PyDict_New(); |
532 | if (op->func_annotations == NULL) Branch (532:13): [True: 0, False: 22.4k]
|
533 | return NULL; |
534 | } |
535 | return func_get_annotation_dict(op); |
536 | } |
537 | |
538 | static int |
539 | func_set_annotations(PyFunctionObject *op, PyObject *value, void *Py_UNUSED(ignored)) |
540 | { |
541 | if (value == Py_None) Branch (541:9): [True: 0, False: 2.88k]
|
542 | value = NULL; |
543 | /* Legal to del f.func_annotations. |
544 | * Can only set func_annotations to NULL (through C api) |
545 | * or a dict. */ |
546 | if (value != NULL && !2.88k PyDict_Check2.88k (value)) { Branch (546:9): [True: 2.88k, False: 1]
Branch (546:26): [True: 0, False: 2.88k]
|
547 | PyErr_SetString(PyExc_TypeError, |
548 | "__annotations__ must be set to a dict object"); |
549 | return -1; |
550 | } |
551 | op->func_version = 0; |
552 | Py_XINCREF(value); |
553 | Py_XSETREF(op->func_annotations, value); |
554 | return 0; |
555 | } |
556 | |
557 | static PyGetSetDef func_getsetlist[] = { |
558 | {"__code__", (getter)func_get_code, (setter)func_set_code}, |
559 | {"__defaults__", (getter)func_get_defaults, |
560 | (setter)func_set_defaults}, |
561 | {"__kwdefaults__", (getter)func_get_kwdefaults, |
562 | (setter)func_set_kwdefaults}, |
563 | {"__annotations__", (getter)func_get_annotations, |
564 | (setter)func_set_annotations}, |
565 | {"__dict__", PyObject_GenericGetDict, PyObject_GenericSetDict}, |
566 | {"__name__", (getter)func_get_name, (setter)func_set_name}, |
567 | {"__qualname__", (getter)func_get_qualname, (setter)func_set_qualname}, |
568 | {NULL} /* Sentinel */ |
569 | }; |
570 | |
571 | /*[clinic input] |
572 | class function "PyFunctionObject *" "&PyFunction_Type" |
573 | [clinic start generated code]*/ |
574 | /*[clinic end generated code: output=da39a3ee5e6b4b0d input=70af9c90aa2e71b0]*/ |
575 | |
576 | #include "clinic/funcobject.c.h" |
577 | |
578 | /* function.__new__() maintains the following invariants for closures. |
579 | The closure must correspond to the free variables of the code object. |
580 | |
581 | if len(code.co_freevars) == 0: |
582 | closure = NULL |
583 | else: |
584 | len(closure) == len(code.co_freevars) |
585 | for every elt in closure, type(elt) == cell |
586 | */ |
587 | |
588 | /*[clinic input] |
589 | @classmethod |
590 | function.__new__ as func_new |
591 | code: object(type="PyCodeObject *", subclass_of="&PyCode_Type") |
592 | a code object |
593 | globals: object(subclass_of="&PyDict_Type") |
594 | the globals dictionary |
595 | name: object = None |
596 | a string that overrides the name from the code object |
597 | argdefs as defaults: object = None |
598 | a tuple that specifies the default argument values |
599 | closure: object = None |
600 | a tuple that supplies the bindings for free variables |
601 | |
602 | Create a function object. |
603 | [clinic start generated code]*/ |
604 | |
605 | static PyObject * |
606 | func_new_impl(PyTypeObject *type, PyCodeObject *code, PyObject *globals, |
607 | PyObject *name, PyObject *defaults, PyObject *closure) |
608 | /*[clinic end generated code: output=99c6d9da3a24e3be input=93611752fc2daf11]*/ |
609 | { |
610 | PyFunctionObject *newfunc; |
611 | Py_ssize_t nclosure; |
612 | |
613 | if (name != Py_None && !1 PyUnicode_Check1 (name)) { Branch (613:9): [True: 1, False: 85]
Branch (613:28): [True: 0, False: 1]
|
614 | PyErr_SetString(PyExc_TypeError, |
615 | "arg 3 (name) must be None or string"); |
616 | return NULL; |
617 | } |
618 | if (defaults != Py_None && !0 PyTuple_Check0 (defaults)) { Branch (618:9): [True: 0, False: 86]
Branch (618:32): [True: 0, False: 0]
|
619 | PyErr_SetString(PyExc_TypeError, |
620 | "arg 4 (defaults) must be None or tuple"); |
621 | return NULL; |
622 | } |
623 | if (!PyTuple_Check(closure)) { Branch (623:9): [True: 85, False: 1]
|
624 | if (code->co_nfreevars && closure == 0 Py_None0 ) { Branch (624:13): [True: 0, False: 85]
Branch (624:35): [True: 0, False: 0]
|
625 | PyErr_SetString(PyExc_TypeError, |
626 | "arg 5 (closure) must be tuple"); |
627 | return NULL; |
628 | } |
629 | else if (closure != Py_None) { Branch (629:18): [True: 0, False: 85]
|
630 | PyErr_SetString(PyExc_TypeError, |
631 | "arg 5 (closure) must be None or tuple"); |
632 | return NULL; |
633 | } |
634 | } |
635 | |
636 | /* check that the closure is well-formed */ |
637 | nclosure = closure == Py_None ? 085 : PyTuple_GET_SIZE1 (closure); Branch (637:16): [True: 85, False: 1]
|
638 | if (code->co_nfreevars != nclosure) Branch (638:9): [True: 0, False: 86]
|
639 | return PyErr_Format(PyExc_ValueError, |
640 | "%U requires closure of length %zd, not %zd", |
641 | code->co_name, code->co_nfreevars, nclosure); |
642 | if (nclosure) { Branch (642:9): [True: 1, False: 85]
|
643 | Py_ssize_t i; |
644 | for (i = 0; i < nclosure; i++1 ) { Branch (644:21): [True: 1, False: 1]
|
645 | PyObject *o = PyTuple_GET_ITEM(closure, i); |
646 | if (!PyCell_Check(o)) { Branch (646:17): [True: 0, False: 1]
|
647 | return PyErr_Format(PyExc_TypeError, |
648 | "arg 5 (closure) expected cell, found %s", |
649 | Py_TYPE(o)->tp_name); |
650 | } |
651 | } |
652 | } |
653 | if (PySys_Audit("function.__new__", "O", code) < 0) { Branch (653:9): [True: 0, False: 86]
|
654 | return NULL; |
655 | } |
656 | |
657 | newfunc = (PyFunctionObject *)PyFunction_New((PyObject *)code, |
658 | globals); |
659 | if (newfunc == NULL) { Branch (659:9): [True: 0, False: 86]
|
660 | return NULL; |
661 | } |
662 | if (name != Py_None) { Branch (662:9): [True: 1, False: 85]
|
663 | Py_INCREF(name); |
664 | Py_SETREF(newfunc->func_name, name); |
665 | } |
666 | if (defaults != Py_None) { Branch (666:9): [True: 0, False: 86]
|
667 | Py_INCREF(defaults); |
668 | newfunc->func_defaults = defaults; |
669 | } |
670 | if (closure != Py_None) { Branch (670:9): [True: 1, False: 85]
|
671 | Py_INCREF(closure); |
672 | newfunc->func_closure = closure; |
673 | } |
674 | |
675 | return (PyObject *)newfunc; |
676 | } |
677 | |
678 | static int |
679 | func_clear(PyFunctionObject *op) |
680 | { |
681 | op->func_version = 0; |
682 | Py_CLEAR(op->func_globals); |
683 | Py_CLEAR(op->func_builtins); |
684 | Py_CLEAR(op->func_module); |
685 | Py_CLEAR(op->func_defaults); |
686 | Py_CLEAR(op->func_kwdefaults); |
687 | Py_CLEAR(op->func_doc); |
688 | Py_CLEAR(op->func_dict); |
689 | Py_CLEAR(op->func_closure); |
690 | Py_CLEAR(op->func_annotations); |
691 | // Don't Py_CLEAR(op->func_code), since code is always required |
692 | // to be non-NULL. Similarly, name and qualname shouldn't be NULL. |
693 | // However, name and qualname could be str subclasses, so they |
694 | // could have reference cycles. The solution is to replace them |
695 | // with a genuinely immutable string. |
696 | Py_SETREF(op->func_name, Py_NewRef(&_Py_STR(empty))); |
697 | Py_SETREF(op->func_qualname, Py_NewRef(&_Py_STR(empty))); |
698 | return 0; |
699 | } |
700 | |
701 | static void |
702 | func_dealloc(PyFunctionObject *op) |
703 | { |
704 | _PyObject_GC_UNTRACK(op); |
705 | if (op->func_weakreflist != NULL) { Branch (705:9): [True: 21, False: 2.57M]
|
706 | PyObject_ClearWeakRefs((PyObject *) op); |
707 | } |
708 | (void)func_clear(op); |
709 | // These aren't cleared by func_clear(). |
710 | Py_DECREF(op->func_code); |
711 | Py_DECREF(op->func_name); |
712 | Py_DECREF(op->func_qualname); |
713 | PyObject_GC_Del(op); |
714 | } |
715 | |
716 | static PyObject* |
717 | func_repr(PyFunctionObject *op) |
718 | { |
719 | return PyUnicode_FromFormat("<function %U at %p>", |
720 | op->func_qualname, op); |
721 | } |
722 | |
723 | static int |
724 | func_traverse(PyFunctionObject *f, visitproc visit, void *arg) |
725 | { |
726 | Py_VISIT(f->func_code); |
727 | Py_VISIT(f->func_globals); |
728 | Py_VISIT(f->func_builtins); |
729 | Py_VISIT(f->func_module); |
730 | Py_VISIT(f->func_defaults); |
731 | Py_VISIT(f->func_kwdefaults); |
732 | Py_VISIT(f->func_doc); |
733 | Py_VISIT(f->func_name); |
734 | Py_VISIT(f->func_dict); |
735 | Py_VISIT(f->func_closure); |
736 | Py_VISIT(f->func_annotations); |
737 | Py_VISIT(f->func_qualname); |
738 | return 0; |
739 | } |
740 | |
741 | /* Bind a function to an object */ |
742 | static PyObject * |
743 | func_descr_get(PyObject *func, PyObject *obj, PyObject *type) |
744 | { |
745 | if (obj == Py_None || obj == NULL) { Branch (745:9): [True: 0, False: 19.7M]
Branch (745:27): [True: 158k, False: 19.6M]
|
746 | Py_INCREF(func); |
747 | return func; |
748 | } |
749 | return PyMethod_New(func, obj); |
750 | } |
751 | |
752 | PyTypeObject PyFunction_Type = { |
753 | PyVarObject_HEAD_INIT(&PyType_Type, 0) |
754 | "function", |
755 | sizeof(PyFunctionObject), |
756 | 0, |
757 | (destructor)func_dealloc, /* tp_dealloc */ |
758 | offsetof(PyFunctionObject, vectorcall), /* tp_vectorcall_offset */ |
759 | 0, /* tp_getattr */ |
760 | 0, /* tp_setattr */ |
761 | 0, /* tp_as_async */ |
762 | (reprfunc)func_repr, /* tp_repr */ |
763 | 0, /* tp_as_number */ |
764 | 0, /* tp_as_sequence */ |
765 | 0, /* tp_as_mapping */ |
766 | 0, /* tp_hash */ |
767 | PyVectorcall_Call, /* tp_call */ |
768 | 0, /* tp_str */ |
769 | 0, /* tp_getattro */ |
770 | 0, /* tp_setattro */ |
771 | 0, /* tp_as_buffer */ |
772 | Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC | |
773 | Py_TPFLAGS_HAVE_VECTORCALL | |
774 | Py_TPFLAGS_METHOD_DESCRIPTOR, /* tp_flags */ |
775 | func_new__doc__, /* tp_doc */ |
776 | (traverseproc)func_traverse, /* tp_traverse */ |
777 | (inquiry)func_clear, /* tp_clear */ |
778 | 0, /* tp_richcompare */ |
779 | offsetof(PyFunctionObject, func_weakreflist), /* tp_weaklistoffset */ |
780 | 0, /* tp_iter */ |
781 | 0, /* tp_iternext */ |
782 | 0, /* tp_methods */ |
783 | func_memberlist, /* tp_members */ |
784 | func_getsetlist, /* tp_getset */ |
785 | 0, /* tp_base */ |
786 | 0, /* tp_dict */ |
787 | func_descr_get, /* tp_descr_get */ |
788 | 0, /* tp_descr_set */ |
789 | offsetof(PyFunctionObject, func_dict), /* tp_dictoffset */ |
790 | 0, /* tp_init */ |
791 | 0, /* tp_alloc */ |
792 | func_new, /* tp_new */ |
793 | }; |
794 | |
795 | |
796 | static int |
797 | functools_copy_attr(PyObject *wrapper, PyObject *wrapped, PyObject *name) |
798 | { |
799 | PyObject *value = PyObject_GetAttr(wrapped, name); |
800 | if (value == NULL) { Branch (800:9): [True: 2.07k, False: 103k]
|
801 | if (PyErr_ExceptionMatches(PyExc_AttributeError)) { Branch (801:13): [True: 2.07k, False: 0]
|
802 | PyErr_Clear(); |
803 | return 0; |
804 | } |
805 | return -1; |
806 | } |
807 | |
808 | int res = PyObject_SetAttr(wrapper, name, value); |
809 | Py_DECREF(value); |
810 | return res; |
811 | } |
812 | |
813 | // Similar to functools.wraps(wrapper, wrapped) |
814 | static int |
815 | functools_wraps(PyObject *wrapper, PyObject *wrapped) |
816 | { |
817 | #define COPY_ATTR(ATTR) \ |
818 | do { \ |
819 | if (functools_copy_attr(wrapper, wrapped, &_Py_ID(ATTR)) < 0) { \ |
820 | return -1; \ |
821 | } \ |
822 | } while (0) \ |
823 | |
824 | COPY_ATTR(__module__); |
825 | COPY_ATTR(__name__); |
826 | COPY_ATTR(__qualname__); |
827 | COPY_ATTR(__doc__); |
828 | COPY_ATTR(__annotations__); |
829 | return 0; |
830 | |
831 | #undef COPY_ATTR |
832 | } |
833 | |
834 | |
835 | /* Class method object */ |
836 | |
837 | /* A class method receives the class as implicit first argument, |
838 | just like an instance method receives the instance. |
839 | To declare a class method, use this idiom: |
840 | |
841 | class C: |
842 | @classmethod |
843 | def f(cls, arg1, arg2, ...): |
844 | ... |
845 | |
846 | It can be called either on the class (e.g. C.f()) or on an instance |
847 | (e.g. C().f()); the instance is ignored except for its class. |
848 | If a class method is called for a derived class, the derived class |
849 | object is passed as the implied first argument. |
850 | |
851 | Class methods are different than C++ or Java static methods. |
852 | If you want those, see static methods below. |
853 | */ |
854 | |
855 | typedef struct { |
856 | PyObject_HEAD |
857 | PyObject *cm_callable; |
858 | PyObject *cm_dict; |
859 | } classmethod; |
860 | |
861 | static void |
862 | cm_dealloc(classmethod *cm) |
863 | { |
864 | _PyObject_GC_UNTRACK((PyObject *)cm); |
865 | Py_XDECREF(cm->cm_callable); |
866 | Py_XDECREF(cm->cm_dict); |
867 | Py_TYPE(cm)->tp_free((PyObject *)cm); |
868 | } |
869 | |
870 | static int |
871 | cm_traverse(classmethod *cm, visitproc visit, void *arg) |
872 | { |
873 | Py_VISIT(cm->cm_callable); |
874 | Py_VISIT(cm->cm_dict); |
875 | return 0; |
876 | } |
877 | |
878 | static int |
879 | cm_clear(classmethod *cm) |
880 | { |
881 | Py_CLEAR(cm->cm_callable); |
882 | Py_CLEAR(cm->cm_dict); |
883 | return 0; |
884 | } |
885 | |
886 | |
887 | static PyObject * |
888 | cm_descr_get(PyObject *self, PyObject *obj, PyObject *type) |
889 | { |
890 | classmethod *cm = (classmethod *)self; |
891 | |
892 | if (cm->cm_callable == NULL) { Branch (892:9): [True: 0, False: 489k]
|
893 | PyErr_SetString(PyExc_RuntimeError, |
894 | "uninitialized classmethod object"); |
895 | return NULL; |
896 | } |
897 | if (type == NULL) Branch (897:9): [True: 6, False: 489k]
|
898 | type = (PyObject *)(Py_TYPE(obj)); |
899 | if (Py_TYPE(cm->cm_callable)->tp_descr_get != NULL) { Branch (899:9): [True: 489k, False: 247]
|
900 | return Py_TYPE(cm->cm_callable)->tp_descr_get(cm->cm_callable, type, |
901 | type); |
902 | } |
903 | return PyMethod_New(cm->cm_callable, type); |
904 | } |
905 | |
906 | static int |
907 | cm_init(PyObject *self, PyObject *args, PyObject *kwds) |
908 | { |
909 | classmethod *cm = (classmethod *)self; |
910 | PyObject *callable; |
911 | |
912 | if (!_PyArg_NoKeywords("classmethod", kwds)) |
913 | return -1; |
914 | if (!PyArg_UnpackTuple(args, "classmethod", 1, 1, &callable)) Branch (914:9): [True: 0, False: 17.1k]
|
915 | return -1; |
916 | Py_INCREF(callable); |
917 | Py_XSETREF(cm->cm_callable, callable); |
918 | |
919 | if (functools_wraps((PyObject *)cm, cm->cm_callable) < 0) { Branch (919:9): [True: 0, False: 17.1k]
|
920 | return -1; |
921 | } |
922 | return 0; |
923 | } |
924 | |
925 | static PyMemberDef cm_memberlist[] = { |
926 | {"__func__", T_OBJECT, offsetof(classmethod, cm_callable), READONLY}, |
927 | {"__wrapped__", T_OBJECT, offsetof(classmethod, cm_callable), READONLY}, |
928 | {NULL} /* Sentinel */ |
929 | }; |
930 | |
931 | static PyObject * |
932 | cm_get___isabstractmethod__(classmethod *cm, void *closure) |
933 | { |
934 | int res = _PyObject_IsAbstract(cm->cm_callable); |
935 | if (res == -1) { Branch (935:9): [True: 0, False: 7.38k]
|
936 | return NULL; |
937 | } |
938 | else if (res) { Branch (938:14): [True: 6, False: 7.37k]
|
939 | Py_RETURN_TRUE; |
940 | } |
941 | Py_RETURN_FALSE7.37k ; |
942 | } |
943 | |
944 | static PyGetSetDef cm_getsetlist[] = { |
945 | {"__isabstractmethod__", |
946 | (getter)cm_get___isabstractmethod__, NULL, NULL, NULL}, |
947 | {"__dict__", PyObject_GenericGetDict, PyObject_GenericSetDict, NULL, NULL}, |
948 | {NULL} /* Sentinel */ |
949 | }; |
950 | |
951 | static PyObject* |
952 | cm_repr(classmethod *cm) |
953 | { |
954 | return PyUnicode_FromFormat("<classmethod(%R)>", cm->cm_callable); |
955 | } |
956 | |
957 | PyDoc_STRVAR(classmethod_doc, |
958 | "classmethod(function) -> method\n\ |
959 | \n\ |
960 | Convert a function to be a class method.\n\ |
961 | \n\ |
962 | A class method receives the class as implicit first argument,\n\ |
963 | just like an instance method receives the instance.\n\ |
964 | To declare a class method, use this idiom:\n\ |
965 | \n\ |
966 | class C:\n\ |
967 | @classmethod\n\ |
968 | def f(cls, arg1, arg2, ...):\n\ |
969 | ...\n\ |
970 | \n\ |
971 | It can be called either on the class (e.g. C.f()) or on an instance\n\ |
972 | (e.g. C().f()). The instance is ignored except for its class.\n\ |
973 | If a class method is called for a derived class, the derived class\n\ |
974 | object is passed as the implied first argument.\n\ |
975 | \n\ |
976 | Class methods are different than C++ or Java static methods.\n\ |
977 | If you want those, see the staticmethod builtin."); |
978 | |
979 | PyTypeObject PyClassMethod_Type = { |
980 | PyVarObject_HEAD_INIT(&PyType_Type, 0) |
981 | "classmethod", |
982 | sizeof(classmethod), |
983 | 0, |
984 | (destructor)cm_dealloc, /* tp_dealloc */ |
985 | 0, /* tp_vectorcall_offset */ |
986 | 0, /* tp_getattr */ |
987 | 0, /* tp_setattr */ |
988 | 0, /* tp_as_async */ |
989 | (reprfunc)cm_repr, /* tp_repr */ |
990 | 0, /* tp_as_number */ |
991 | 0, /* tp_as_sequence */ |
992 | 0, /* tp_as_mapping */ |
993 | 0, /* tp_hash */ |
994 | 0, /* tp_call */ |
995 | 0, /* tp_str */ |
996 | 0, /* tp_getattro */ |
997 | 0, /* tp_setattro */ |
998 | 0, /* tp_as_buffer */ |
999 | Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC, |
1000 | classmethod_doc, /* tp_doc */ |
1001 | (traverseproc)cm_traverse, /* tp_traverse */ |
1002 | (inquiry)cm_clear, /* tp_clear */ |
1003 | 0, /* tp_richcompare */ |
1004 | 0, /* tp_weaklistoffset */ |
1005 | 0, /* tp_iter */ |
1006 | 0, /* tp_iternext */ |
1007 | 0, /* tp_methods */ |
1008 | cm_memberlist, /* tp_members */ |
1009 | cm_getsetlist, /* tp_getset */ |
1010 | 0, /* tp_base */ |
1011 | 0, /* tp_dict */ |
1012 | cm_descr_get, /* tp_descr_get */ |
1013 | 0, /* tp_descr_set */ |
1014 | offsetof(classmethod, cm_dict), /* tp_dictoffset */ |
1015 | cm_init, /* tp_init */ |
1016 | PyType_GenericAlloc, /* tp_alloc */ |
1017 | PyType_GenericNew, /* tp_new */ |
1018 | PyObject_GC_Del, /* tp_free */ |
1019 | }; |
1020 | |
1021 | PyObject * |
1022 | PyClassMethod_New(PyObject *callable) |
1023 | { |
1024 | classmethod *cm = (classmethod *) |
1025 | PyType_GenericAlloc(&PyClassMethod_Type, 0); |
1026 | if (cm != NULL) { Branch (1026:9): [True: 106, False: 0]
|
1027 | Py_INCREF(callable); |
1028 | cm->cm_callable = callable; |
1029 | } |
1030 | return (PyObject *)cm; |
1031 | } |
1032 | |
1033 | |
1034 | /* Static method object */ |
1035 | |
1036 | /* A static method does not receive an implicit first argument. |
1037 | To declare a static method, use this idiom: |
1038 | |
1039 | class C: |
1040 | @staticmethod |
1041 | def f(arg1, arg2, ...): |
1042 | ... |
1043 | |
1044 | It can be called either on the class (e.g. C.f()) or on an instance |
1045 | (e.g. C().f()). Both the class and the instance are ignored, and |
1046 | neither is passed implicitly as the first argument to the method. |
1047 | |
1048 | Static methods in Python are similar to those found in Java or C++. |
1049 | For a more advanced concept, see class methods above. |
1050 | */ |
1051 | |
1052 | typedef struct { |
1053 | PyObject_HEAD |
1054 | PyObject *sm_callable; |
1055 | PyObject *sm_dict; |
1056 | } staticmethod; |
1057 | |
1058 | static void |
1059 | sm_dealloc(staticmethod *sm) |
1060 | { |
1061 | _PyObject_GC_UNTRACK((PyObject *)sm); |
1062 | Py_XDECREF(sm->sm_callable); |
1063 | Py_XDECREF(sm->sm_dict); |
1064 | Py_TYPE(sm)->tp_free((PyObject *)sm); |
1065 | } |
1066 | |
1067 | static int |
1068 | sm_traverse(staticmethod *sm, visitproc visit, void *arg) |
1069 | { |
1070 | Py_VISIT(sm->sm_callable); |
1071 | Py_VISIT(sm->sm_dict); |
1072 | return 0; |
1073 | } |
1074 | |
1075 | static int |
1076 | sm_clear(staticmethod *sm) |
1077 | { |
1078 | Py_CLEAR(sm->sm_callable); |
1079 | Py_CLEAR(sm->sm_dict); |
1080 | return 0; |
1081 | } |
1082 | |
1083 | static PyObject * |
1084 | sm_descr_get(PyObject *self, PyObject *obj, PyObject *type) |
1085 | { |
1086 | staticmethod *sm = (staticmethod *)self; |
1087 | |
1088 | if (sm->sm_callable == NULL) { Branch (1088:9): [True: 0, False: 3.37M]
|
1089 | PyErr_SetString(PyExc_RuntimeError, |
1090 | "uninitialized staticmethod object"); |
1091 | return NULL; |
1092 | } |
1093 | Py_INCREF(sm->sm_callable); |
1094 | return sm->sm_callable; |
1095 | } |
1096 | |
1097 | static int |
1098 | sm_init(PyObject *self, PyObject *args, PyObject *kwds) |
1099 | { |
1100 | staticmethod *sm = (staticmethod *)self; |
1101 | PyObject *callable; |
1102 | |
1103 | if (!_PyArg_NoKeywords("staticmethod", kwds)) |
1104 | return -1; |
1105 | if (!PyArg_UnpackTuple(args, "staticmethod", 1, 1, &callable)) Branch (1105:9): [True: 0, False: 4.09k]
|
1106 | return -1; |
1107 | Py_INCREF(callable); |
1108 | Py_XSETREF(sm->sm_callable, callable); |
1109 | |
1110 | if (functools_wraps((PyObject *)sm, sm->sm_callable) < 0) { Branch (1110:9): [True: 0, False: 4.09k]
|
1111 | return -1; |
1112 | } |
1113 | return 0; |
1114 | } |
1115 | |
1116 | static PyObject* |
1117 | sm_call(PyObject *callable, PyObject *args, PyObject *kwargs) |
1118 | { |
1119 | staticmethod *sm = (staticmethod *)callable; |
1120 | return PyObject_Call(sm->sm_callable, args, kwargs); |
1121 | } |
1122 | |
1123 | static PyMemberDef sm_memberlist[] = { |
1124 | {"__func__", T_OBJECT, offsetof(staticmethod, sm_callable), READONLY}, |
1125 | {"__wrapped__", T_OBJECT, offsetof(staticmethod, sm_callable), READONLY}, |
1126 | {NULL} /* Sentinel */ |
1127 | }; |
1128 | |
1129 | static PyObject * |
1130 | sm_get___isabstractmethod__(staticmethod *sm, void *closure) |
1131 | { |
1132 | int res = _PyObject_IsAbstract(sm->sm_callable); |
1133 | if (res == -1) { Branch (1133:9): [True: 0, False: 136]
|
1134 | return NULL; |
1135 | } |
1136 | else if (res) { Branch (1136:14): [True: 4, False: 132]
|
1137 | Py_RETURN_TRUE; |
1138 | } |
1139 | Py_RETURN_FALSE132 ; |
1140 | } |
1141 | |
1142 | static PyGetSetDef sm_getsetlist[] = { |
1143 | {"__isabstractmethod__", |
1144 | (getter)sm_get___isabstractmethod__, NULL, NULL, NULL}, |
1145 | {"__dict__", PyObject_GenericGetDict, PyObject_GenericSetDict, NULL, NULL}, |
1146 | {NULL} /* Sentinel */ |
1147 | }; |
1148 | |
1149 | static PyObject* |
1150 | sm_repr(staticmethod *sm) |
1151 | { |
1152 | return PyUnicode_FromFormat("<staticmethod(%R)>", sm->sm_callable); |
1153 | } |
1154 | |
1155 | PyDoc_STRVAR(staticmethod_doc, |
1156 | "staticmethod(function) -> method\n\ |
1157 | \n\ |
1158 | Convert a function to be a static method.\n\ |
1159 | \n\ |
1160 | A static method does not receive an implicit first argument.\n\ |
1161 | To declare a static method, use this idiom:\n\ |
1162 | \n\ |
1163 | class C:\n\ |
1164 | @staticmethod\n\ |
1165 | def f(arg1, arg2, ...):\n\ |
1166 | ...\n\ |
1167 | \n\ |
1168 | It can be called either on the class (e.g. C.f()) or on an instance\n\ |
1169 | (e.g. C().f()). Both the class and the instance are ignored, and\n\ |
1170 | neither is passed implicitly as the first argument to the method.\n\ |
1171 | \n\ |
1172 | Static methods in Python are similar to those found in Java or C++.\n\ |
1173 | For a more advanced concept, see the classmethod builtin."); |
1174 | |
1175 | PyTypeObject PyStaticMethod_Type = { |
1176 | PyVarObject_HEAD_INIT(&PyType_Type, 0) |
1177 | "staticmethod", |
1178 | sizeof(staticmethod), |
1179 | 0, |
1180 | (destructor)sm_dealloc, /* tp_dealloc */ |
1181 | 0, /* tp_vectorcall_offset */ |
1182 | 0, /* tp_getattr */ |
1183 | 0, /* tp_setattr */ |
1184 | 0, /* tp_as_async */ |
1185 | (reprfunc)sm_repr, /* tp_repr */ |
1186 | 0, /* tp_as_number */ |
1187 | 0, /* tp_as_sequence */ |
1188 | 0, /* tp_as_mapping */ |
1189 | 0, /* tp_hash */ |
1190 | sm_call, /* tp_call */ |
1191 | 0, /* tp_str */ |
1192 | 0, /* tp_getattro */ |
1193 | 0, /* tp_setattro */ |
1194 | 0, /* tp_as_buffer */ |
1195 | Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC, |
1196 | staticmethod_doc, /* tp_doc */ |
1197 | (traverseproc)sm_traverse, /* tp_traverse */ |
1198 | (inquiry)sm_clear, /* tp_clear */ |
1199 | 0, /* tp_richcompare */ |
1200 | 0, /* tp_weaklistoffset */ |
1201 | 0, /* tp_iter */ |
1202 | 0, /* tp_iternext */ |
1203 | 0, /* tp_methods */ |
1204 | sm_memberlist, /* tp_members */ |
1205 | sm_getsetlist, /* tp_getset */ |
1206 | 0, /* tp_base */ |
1207 | 0, /* tp_dict */ |
1208 | sm_descr_get, /* tp_descr_get */ |
1209 | 0, /* tp_descr_set */ |
1210 | offsetof(staticmethod, sm_dict), /* tp_dictoffset */ |
1211 | sm_init, /* tp_init */ |
1212 | PyType_GenericAlloc, /* tp_alloc */ |
1213 | PyType_GenericNew, /* tp_new */ |
1214 | PyObject_GC_Del, /* tp_free */ |
1215 | }; |
1216 | |
1217 | PyObject * |
1218 | PyStaticMethod_New(PyObject *callable) |
1219 | { |
1220 | staticmethod *sm = (staticmethod *) |
1221 | PyType_GenericAlloc(&PyStaticMethod_Type, 0); |
1222 | if (sm != NULL) { Branch (1222:9): [True: 2.37k, False: 0]
|
1223 | Py_INCREF(callable); |
1224 | sm->sm_callable = callable; |
1225 | } |
1226 | return (PyObject *)sm; |
1227 | } |