Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 1 addition & 2 deletions Lib/test/test_inspect/test_inspect.py
Original file line number Diff line number Diff line change
Expand Up @@ -6547,8 +6547,7 @@ def test_warnings_module_has_signatures(self):

def test_weakref_module_has_signatures(self):
import weakref
no_signature = {'ReferenceType', 'ref'}
self._test_module_has_signatures(weakref, no_signature)
self._test_module_has_signatures(weakref)

def test_python_function_override_signature(self):
def func(*args, **kwargs):
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Speed up creating :class:`weakref.ref` objects by adding a vectorcall implementation of the constructor generated by Argument Clinic. Patch by Pieter Eendebak.
107 changes: 106 additions & 1 deletion Objects/clinic/weakrefobject.c.h

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

69 changes: 41 additions & 28 deletions Objects/weakrefobject.c
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,10 @@
#include "pycore_weakref.h" // _PyWeakref_GET_REF()

/*[clinic input]
class weakref "PyWeakReference *" "&_PyWeakref_RefType"
module weakref
class weakref.ReferenceType "PyWeakReference *" "&_PyWeakref_RefType"
[clinic start generated code]*/
/*[clinic end generated code: output=da39a3ee5e6b4b0d input=ad66c8b0acee6ad9]*/
/*[clinic end generated code: output=da39a3ee5e6b4b0d input=25211e4a7d687f3f]*/

#include "clinic/weakrefobject.c.h"

Expand Down Expand Up @@ -195,12 +196,12 @@ weakref_vectorcall(PyObject *self, PyObject *const *args,

/*[clinic input]
@critical_section
weakref.__hash__
weakref.ReferenceType.__hash__ as weakref_hash
[clinic start generated code]*/

static Py_hash_t
weakref_hash_impl(PyWeakReference *self)
/*[clinic end generated code: output=4904eacaabf902c9 input=703596f4b120e47c]*/
/*[clinic end generated code: output=4904eacaabf902c9 input=f248ec0b25c064e0]*/
{
if (self->hash != -1)
return self->hash;
Expand Down Expand Up @@ -465,35 +466,45 @@ get_or_create_weakref(PyTypeObject *type, PyObject *obj, PyObject *callback)
}
}

static int
parse_weakref_init_args(const char *funcname, PyObject *args, PyObject *kwargs,
PyObject **obp, PyObject **callbackp)
{
return PyArg_UnpackTuple(args, funcname, 1, 2, obp, callbackp);
}
/*[clinic input]
@classmethod
@vectorcall
weakref.ReferenceType.__new__ as weakref_ref_new

object: object
callback: object(c_default="NULL") = None
/

Create a weak reference to object.

Calling the reference returns object, or None once it has been garbage
collected. If callback is given, it is called with the reference as
its only argument when object is about to be finalized.
[clinic start generated code]*/

static PyObject *
weakref___new__(PyTypeObject *type, PyObject *args, PyObject *kwargs)
weakref_ref_new_impl(PyTypeObject *type, PyObject *object,
PyObject *callback)
/*[clinic end generated code: output=0b84aee8668f4c2f input=0cd09b468ebb6371]*/
{
PyObject *ob, *callback = NULL;
if (parse_weakref_init_args("__new__", args, kwargs, &ob, &callback)) {
return (PyObject *)get_or_create_weakref(type, ob, callback);
}
return NULL;
return (PyObject *)get_or_create_weakref(type, object, callback);
}

static int
weakref___init__(PyObject *self, PyObject *args, PyObject *kwargs)
{
PyObject *tmp;
/*[clinic input]
weakref.ReferenceType.__init__ as weakref_ref_init

if (!_PyArg_NoKeywords("ref", kwargs))
return -1;
object: object
callback: object = None
/
[clinic start generated code]*/

if (parse_weakref_init_args("__init__", args, kwargs, &tmp, &tmp))
return 0;
else
return -1;
static int
weakref_ref_init_impl(PyWeakReference *self, PyObject *object,
PyObject *callback)
/*[clinic end generated code: output=d36cfa9ccd36856e input=373a3e3f2841a4fa]*/
{
/* The arguments were already used by __new__; only validate them. */
return 0;
}


Expand All @@ -514,6 +525,7 @@ _PyWeakref_RefType = {
PyVarObject_HEAD_INIT(&PyType_Type, 0)
.tp_name = "weakref.ReferenceType",
.tp_basicsize = sizeof(PyWeakReference),
.tp_doc = weakref_ref_new__doc__,
.tp_dealloc = weakref_dealloc,
.tp_vectorcall_offset = offsetof(PyWeakReference, vectorcall),
.tp_call = PyVectorcall_Call,
Expand All @@ -526,10 +538,11 @@ _PyWeakref_RefType = {
.tp_richcompare = weakref_richcompare,
.tp_methods = weakref_methods,
.tp_members = weakref_members,
.tp_init = weakref___init__,
.tp_init = weakref_ref_init,
.tp_alloc = PyType_GenericAlloc,
.tp_new = weakref___new__,
.tp_new = weakref_ref_new,
.tp_free = PyObject_GC_Del,
.tp_vectorcall = weakref_ref_vectorcall,
};


Expand Down
Loading