Skip to content
Open
Show file tree
Hide file tree
Changes from 2 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
8 changes: 7 additions & 1 deletion Doc/c-api/refcounting.rst
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ of Python objects.
references to the object are actually held. For example, some
objects are :term:`immortal` and have a very high refcount that does not
reflect the actual number of references. Consequently, do not rely
on the returned value to be accurate, other than a value of 0 or 1.
on the returned value to be accurate.

Use the :c:func:`Py_SET_REFCNT()` function to set an object reference count.

Expand All @@ -38,6 +38,12 @@ of Python objects.
.. versionchanged:: 3.11
The parameter type is no longer :c:expr:`const PyObject*`.

.. versionchanged:: 3.14
The interpreter now uses :term:`borrowed references <borrowed reference>`
where possible when calling C extensions. This means that an object's
reference count may appear as 1, even when it is not solely referenced by
the caller.


.. c:function:: void Py_SET_REFCNT(PyObject *o, Py_ssize_t refcnt)

Expand Down
10 changes: 6 additions & 4 deletions Doc/whatsnew/3.14.rst
Original file line number Diff line number Diff line change
Expand Up @@ -3046,10 +3046,12 @@ Porting to Python 3.14
* The interpreter internally avoids some reference count modifications when
loading objects onto the operands stack by :term:`borrowing <borrowed reference>`
references when possible. This can lead to smaller reference count values
compared to previous Python versions. C API extensions that checked
:c:func:`Py_REFCNT` of ``1`` to determine if an function argument is not
referenced by any other code should instead use
:c:func:`PyUnstable_Object_IsUniqueReferencedTemporary` as a safer replacement.
compared to previous Python versions, because the creation of :term:`strong
references <strong reference>` is avoided in the Python interpreter. This
generally does not affect existing code, but C API extensions that checked
:c:func:`Py_REFCNT` of ``1`` to determine if an object is not referenced by
any other code should instead use :c:func:`PyUnstable_Object_IsUniqueReferencedTemporary`
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It doesn't feel great to suggest people move from a (theoretically) stable Py_REFCNT(op) == 1 to an explicitly unstable PyUnstable_ function.

Can we explain why the function we suggest users port to is marked as unstable (e.g. that in reality, Py_REFCNT(op) == 1 was less stable than it appeared?).

Per Petr's comment on the issue, if this is strictly a breaking change, the note in refcounting.rst should probably be more explicit that in previous versions, the semantics around 1 and 0 were guaranteed, but that they no longer are.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

0 is still guaranteed, as far as I know. I'll do my best to make things clearer otherwise.

Copy link
Member Author

@ZeroIntensity ZeroIntensity Aug 15, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've updated both notes. Let me know if that looks any better.

as a safer replacement.


* Private functions promoted to public C APIs:
Expand Down
Loading