New submission from Daniel Alley <dal...@redhat.com>:

Disclaimer: I'm not familiar with the interpreter internals, nor am I really a 
C dev, so I could be misinterpreting these results due to inexperience.

I've been attempting to debug a memory leak which I thought was caused by a C 
API extension that we are using.  When running the unit tests for this library 
under valgrind, I get a couple of results like the following, where the bottom 
of the call stack is a realloc() triggered by _PyUnicodeWriter_Finish()

==5732== 76 bytes in 1 blocks are definitely lost in loss record 4,571 of 9,822
==5732==    at 0x4C2C291: realloc (vg_replace_malloc.c:836)
==5732==    by 0x4F52323: _PyUnicodeWriter_Finish (in 
/usr/lib64/libpython3.6m.so.1.0)
==5732==    by 0x4F5A087: PyUnicode_FromFormatV (in 
/usr/lib64/libpython3.6m.so.1.0)
==5732==    by 0x4F937BC: PyErr_FormatV (in /usr/lib64/libpython3.6m.so.1.0)
==5732==    by 0x4F93433: PyErr_Format (in /usr/lib64/libpython3.6m.so.1.0)
==5732==    by 0x4F836B9: _PyEval_EvalFrameDefault (in 
/usr/lib64/libpython3.6m.so.1.0)
==5732==    by 0x4F87C9E: PyEval_EvalCodeEx (in /usr/lib64/libpython3.6m.so.1.0)
==5732==    by 0x4EF6DE2: ??? (in /usr/lib64/libpython3.6m.so.1.0)
==5732==    by 0x4EDEF62: PyObject_Call (in /usr/lib64/libpython3.6m.so.1.0)
==5732==    by 0xF9785EF: c_warningcb (in 
/usr/local/lib/pulp/lib/python3.6/site-packages/createrepo_c/_createrepo_c.so)
==5732==    by 0xF98F897: cr_xml_parser_warning (in 
/usr/local/lib/pulp/lib/python3.6/site-packages/createrepo_c/_createrepo_c.so)
==5732==    by 0xF98B59E: cr_start_handler (in 
/usr/local/lib/pulp/lib/python3.6/site-packages/createrepo_c/_createrepo_c.so)

There is no explicit call to realloc() in that function, but there is a call to 
resize_compact(), which in turn calls PyObject_Realloc(). I assume all those 
are getting inlined which is why it looks like there's nothing in-beteween -- 
if not, then maybe the leak is actually somewhere else.

The following is speculation given that I have limited understanding of 
interpreter workings.

In the version of Python I am using (3.6), resize_compact() has some code that 
looks suspicious to me: [0]

Two things jump out: 

1) "_Py_ForgetReference(unicode)", which according to this mailing list email 
[1] is used "to avoid having the deallocator run as result of the
DECREF".  The definition and usage of "_Py_ForgetReference(unicode)" in newer 
versions of Python is hidden behind "#ifdef Py_TRACE_REFS" flags [2], but it 
was not being done previously, which raises the question if perhaps it was 
being used improperly in previous versions. Forgetting about an object without 
deallocating it would certainly cause a leak.

2) When comparing [0] to a nearly identical piece of code meant for resizing 
bytestrings [3], I notice that in the branch handling the out of memory case, 
the bytestring version calls "PyObject_Del()" whereas the unicode version calls 
"_Py_NewReference()".

Can someone with more knowledge take a look at this?  And if neither of these 
are "the problem" then perhaps help me investigate what might be causing this 
Valgrind output?


[0] https://github.com/python/cpython/blob/3.6/Objects/unicodeobject.c#L943-L952

[1] https://www.mail-archive.com/python-dev@python.org/msg108525.html

[2] 
https://github.com/python/cpython/pull/18332/files#diff-34c966e7876d6f8bf801dd51896327e4f68bba02cddb95fbf3963f0b2e39c38aR1043-R1045

[3] https://github.com/python/cpython/blob/3.6/Objects/bytesobject.c#L3006-L3015

----------
components: Interpreter Core
messages: 380077
nosy: dralley
priority: normal
severity: normal
status: open
title: Potential memory leak in resize_compact() (for unicode objects)
type: resource usage
versions: Python 3.6

_______________________________________
Python tracker <rep...@bugs.python.org>
<https://bugs.python.org/issue42221>
_______________________________________
_______________________________________________
Python-bugs-list mailing list
Unsubscribe: 
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com

Reply via email to