mirror of
https://github.com/python/cpython.git
synced 2026-10-28 18:35:21 +08:00
gh-136872: Build pymalloc in sanitizer builds, but disable it by default (GH-157934)
--with-*address-sanitizer and --with-memory-sanitizer unconditionally disabled pymalloc (even when --with-pymalloc was given explicitly). Enable it, so that it's available with `PYTHONMALLOC=pymalloc`. Disable it by default on the affected sanitizer builds.
This commit is contained in:
1 parent
acfa77671c
commit
2791c35cae
9 files changed
+48
-28
No files matched your search
+11
-3
@@ -437,6 +437,8 @@ Release build ``"pymalloc"`` ``malloc``
|
||||
Debug build ``"pymalloc_debug"`` ``malloc`` + debug ``pymalloc`` + debug ``pymalloc`` + debug
|
||||
Release build, without pymalloc ``"malloc"`` ``malloc`` ``malloc`` ``malloc``
|
||||
Debug build, without pymalloc ``"malloc_debug"`` ``malloc`` + debug ``malloc`` + debug ``malloc`` + debug
|
||||
Release build, with ASan or MSan ``"malloc"`` ``malloc`` ``malloc`` ``malloc``
|
||||
Debug build, with ASan or MSan ``"malloc_debug"`` ``malloc`` + debug ``malloc`` + debug ``malloc`` + debug
|
||||
Free-threaded build ``"mimalloc"`` ``mimalloc`` ``mimalloc`` ``mimalloc``
|
||||
Free-threaded debug build ``"mimalloc_debug"`` ``mimalloc`` + debug ``mimalloc`` + debug ``mimalloc`` + debug
|
||||
=================================== ======================= ==================== ====================== ======================
|
||||
@@ -451,6 +453,10 @@ Legend:
|
||||
* "+ debug": with :ref:`debug hooks on the Python memory allocators
|
||||
<pymem-debug-hooks>`.
|
||||
* "Debug build": :ref:`Python build in debug mode <debug-build>`.
|
||||
* "with ASan or MSan": sanitizer build as configured using the
|
||||
:option:`--with-address-sanitizer`,
|
||||
:option:`--with-hwaddress-sanitizer`, and/or
|
||||
:option:`--with-memory-sanitizer` option.
|
||||
|
||||
.. _customize-memory-allocators:
|
||||
|
||||
@@ -705,9 +711,11 @@ This allocator is disabled if Python is configured with the
|
||||
:option:`--without-pymalloc` option. It can also be disabled at runtime using
|
||||
the :envvar:`PYTHONMALLOC` environment variable (ex: ``PYTHONMALLOC=malloc``).
|
||||
|
||||
Typically, it makes sense to disable the pymalloc allocator when building
|
||||
Python with AddressSanitizer (:option:`--with-address-sanitizer`) which helps
|
||||
uncover low level bugs within the C code.
|
||||
The pymalloc allocator is disabled by default when Python is built with
|
||||
a sanitizer which does not track pymalloc allocations
|
||||
(:option:`--with-address-sanitizer`, :option:`--with-hwaddress-sanitizer`,
|
||||
:option:`--with-memory-sanitizer`).
|
||||
Use :envvar:`PYTHONMALLOC=pymalloc <PYTHONMALLOC>` to enable pymalloc.
|
||||
|
||||
Customize pymalloc Arena Allocator
|
||||
----------------------------------
|
||||
|
||||
@@ -1016,9 +1016,9 @@ Debug options
|
||||
.. option:: --with-address-sanitizer
|
||||
|
||||
Enable AddressSanitizer memory error detector, ``asan`` (default is no).
|
||||
To improve ASan detection capabilities you may also want to combine this
|
||||
with :option:`--without-pymalloc` to disable the specialized small-object
|
||||
allocator whose allocations are not tracked by ASan.
|
||||
|
||||
When built with ``asan``, Python uses ``malloc`` instead of :ref:`pymalloc <pymalloc>` by default.
|
||||
Set :envvar:`PYTHONMALLOC=pymalloc <PYTHONMALLOC>` to use pymalloc.
|
||||
|
||||
.. versionadded:: 3.6
|
||||
|
||||
@@ -1033,6 +1033,9 @@ Debug options
|
||||
<https://clang.llvm.org/docs/HardwareAssistedAddressSanitizerDesign.html>`_
|
||||
for more information.
|
||||
|
||||
When built with ``hwasan``, Python uses ``malloc`` instead of :ref:`pymalloc <pymalloc>` by default.
|
||||
Set :envvar:`PYTHONMALLOC=pymalloc <PYTHONMALLOC>` to use pymalloc.
|
||||
|
||||
.. versionadded:: next
|
||||
|
||||
.. option:: --with-memory-sanitizer
|
||||
@@ -1043,6 +1046,9 @@ Debug options
|
||||
not built with MSan, so either build all dependencies with MSan or disable
|
||||
the extension modules that use them in :file:`Modules/Setup.local`.
|
||||
|
||||
When built with ``msan``, Python uses ``malloc`` instead of :ref:`pymalloc <pymalloc>` by default.
|
||||
Set :envvar:`PYTHONMALLOC=pymalloc <PYTHONMALLOC>` to use pymalloc.
|
||||
|
||||
.. versionadded:: 3.6
|
||||
|
||||
.. option:: --with-undefined-behavior-sanitizer
|
||||
|
||||
@@ -36,6 +36,10 @@ extern void _PyMem_MiRawFree(void *, void *);
|
||||
extern void* _PyMem_MiRawRealloc(void *, void *, size_t);
|
||||
# undef PYRAW_ALLOC
|
||||
# define PYRAW_ALLOC {NULL, _PyMem_MiRawMalloc, _PyMem_MiRawCalloc, _PyMem_MiRawRealloc, _PyMem_MiRawFree}
|
||||
#elif defined(_Py_ADDRESS_SANITIZER) || defined(_Py_MEMORY_SANITIZER)
|
||||
// Keep in sync with the default allocators in Objects/obmalloc.c.
|
||||
# define PYOBJ_ALLOC PYRAW_ALLOC
|
||||
# define PYMEM_ALLOC PYOBJ_ALLOC
|
||||
#elif defined(WITH_PYMALLOC)
|
||||
extern void* _PyObject_Malloc(void *, size_t);
|
||||
extern void* _PyObject_Calloc(void *, size_t, size_t);
|
||||
|
||||
@@ -845,10 +845,13 @@ class CmdLineTest(unittest.TestCase):
|
||||
code = "import _testinternalcapi; print(_testinternalcapi.pymem_getallocatorsname())"
|
||||
with support.SuppressCrashReport():
|
||||
out = self.run_xdev("-c", code, check_exitcode=False)
|
||||
if support.with_pymalloc():
|
||||
alloc_name = "pymalloc_debug"
|
||||
elif support.Py_GIL_DISABLED:
|
||||
if support.Py_GIL_DISABLED:
|
||||
alloc_name = "mimalloc_debug"
|
||||
elif support.check_sanitizer(address=True, memory=True):
|
||||
# ASan and MSan builds default to malloc, even with pymalloc.
|
||||
alloc_name = "malloc_debug"
|
||||
elif support.with_pymalloc():
|
||||
alloc_name = "pymalloc_debug"
|
||||
else:
|
||||
alloc_name = "malloc_debug"
|
||||
self.assertEqual(out, alloc_name)
|
||||
@@ -927,10 +930,15 @@ class CmdLineTest(unittest.TestCase):
|
||||
# Test the PYTHONMALLOC environment variable
|
||||
malloc = not support.Py_GIL_DISABLED
|
||||
pymalloc = support.with_pymalloc()
|
||||
sanitizer = support.check_sanitizer(address=True, memory=True)
|
||||
mimalloc = support.with_mimalloc()
|
||||
if support.Py_GIL_DISABLED:
|
||||
default_name = 'mimalloc_debug' if support.Py_DEBUG else 'mimalloc'
|
||||
default_name_debug = 'mimalloc_debug'
|
||||
elif sanitizer:
|
||||
# ASan and MSan builds default to malloc, even with pymalloc.
|
||||
default_name = 'malloc_debug' if support.Py_DEBUG else 'malloc'
|
||||
default_name_debug = 'malloc_debug'
|
||||
elif pymalloc:
|
||||
default_name = 'pymalloc_debug' if support.Py_DEBUG else 'pymalloc'
|
||||
default_name_debug = 'pymalloc_debug'
|
||||
|
||||
@@ -1194,8 +1194,10 @@ class SysModuleTest(unittest.TestCase):
|
||||
# The sysconfig vars are not available on Windows.
|
||||
if sys.platform != "win32":
|
||||
with_pymalloc = sysconfig.get_config_var("WITH_PYMALLOC")
|
||||
with_sanitizer = support.check_sanitizer(address=True, memory=True)
|
||||
self.assertIn(b"free PyDictObjects", err)
|
||||
if with_pymalloc:
|
||||
# ASan and MSan builds default to malloc, even with pymalloc.
|
||||
if with_pymalloc and not with_sanitizer:
|
||||
self.assertIn(b'Small block threshold', err)
|
||||
|
||||
# The function has no parameter
|
||||
|
||||
@@ -0,0 +1,4 @@
|
||||
Python built with :option:`--with-address-sanitizer` or
|
||||
:option:`--with-memory-sanitizer` now includes pymalloc, but uses ``malloc``
|
||||
as the default memory allocator. Set
|
||||
:envvar:`PYTHONMALLOC=pymalloc <PYTHONMALLOC>` to use pymalloc.
|
||||
@@ -433,6 +433,12 @@ void* _PyObject_Realloc(void *ctx, void *ptr, size_t size);
|
||||
# define PYRAW_ALLOC MIMALLOC_RAWALLOC
|
||||
# define PYMEM_ALLOC MIMALLOC_ALLOC
|
||||
# define PYOBJ_ALLOC MIMALLOC_OBJALLOC
|
||||
#elif defined(_Py_ADDRESS_SANITIZER) || defined(_Py_MEMORY_SANITIZER)
|
||||
// ASan and MSan do not track pymalloc blocks, so use malloc by default.
|
||||
// pymalloc can still be selected at runtime.
|
||||
# define PYRAW_ALLOC MALLOC_ALLOC
|
||||
# define PYMEM_ALLOC MALLOC_ALLOC
|
||||
# define PYOBJ_ALLOC MALLOC_ALLOC
|
||||
#elif defined(WITH_PYMALLOC)
|
||||
# define PYRAW_ALLOC MALLOC_ALLOC
|
||||
# define PYMEM_ALLOC PYMALLOC_ALLOC
|
||||
|
||||
@@ -14151,8 +14151,6 @@ then :
|
||||
printf "%s\n" "$withval" >&6; }
|
||||
BASECFLAGS="-fsanitize=address -fno-omit-frame-pointer $BASECFLAGS"
|
||||
LDFLAGS="-fsanitize=address $LDFLAGS"
|
||||
# ASan works by controlling memory allocation, our own malloc interferes.
|
||||
with_pymalloc="no"
|
||||
|
||||
else case e in #(
|
||||
e) { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5
|
||||
@@ -14227,11 +14225,6 @@ else case e in #(
|
||||
esac
|
||||
fi
|
||||
|
||||
# HWASan works by controlling memory allocation, our own malloc interferes,
|
||||
# so disable it by default, but allow --with-pymalloc to override.
|
||||
if test -z "$with_pymalloc"; then
|
||||
with_pymalloc="no"
|
||||
fi
|
||||
|
||||
else case e in #(
|
||||
e) { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5
|
||||
@@ -14293,8 +14286,6 @@ else case e in #(
|
||||
esac
|
||||
fi
|
||||
|
||||
# MSan works by controlling memory allocation, our own malloc interferes.
|
||||
with_pymalloc="no"
|
||||
|
||||
else case e in #(
|
||||
e) { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5
|
||||
|
||||
@@ -3526,8 +3526,6 @@ AC_ARG_WITH([address_sanitizer],
|
||||
AC_MSG_RESULT([$withval])
|
||||
BASECFLAGS="-fsanitize=address -fno-omit-frame-pointer $BASECFLAGS"
|
||||
LDFLAGS="-fsanitize=address $LDFLAGS"
|
||||
# ASan works by controlling memory allocation, our own malloc interferes.
|
||||
with_pymalloc="no"
|
||||
],
|
||||
[AC_MSG_RESULT([no])])
|
||||
|
||||
@@ -3551,11 +3549,6 @@ AX_CHECK_COMPILE_FLAG([$hwasan_flags],[
|
||||
BASECFLAGS="$hwasan_flags -fno-omit-frame-pointer $BASECFLAGS"
|
||||
LDFLAGS="$hwasan_flags $LDFLAGS"
|
||||
],[AC_MSG_ERROR([The selected compiler doesn't support hardware address sanitizer])])
|
||||
# HWASan works by controlling memory allocation, our own malloc interferes,
|
||||
# so disable it by default, but allow --with-pymalloc to override.
|
||||
if test -z "$with_pymalloc"; then
|
||||
with_pymalloc="no"
|
||||
fi
|
||||
],
|
||||
[AC_MSG_RESULT([no])])
|
||||
|
||||
@@ -3572,8 +3565,6 @@ AX_CHECK_COMPILE_FLAG([-fsanitize=memory],[
|
||||
BASECFLAGS="-fsanitize=memory -fsanitize-memory-track-origins=2 -fno-omit-frame-pointer $BASECFLAGS"
|
||||
LDFLAGS="-fsanitize=memory -fsanitize-memory-track-origins=2 $LDFLAGS"
|
||||
],[AC_MSG_ERROR([The selected compiler doesn't support memory sanitizer])])
|
||||
# MSan works by controlling memory allocation, our own malloc interferes.
|
||||
with_pymalloc="no"
|
||||
],
|
||||
[AC_MSG_RESULT([no])])
|
||||
|
||||
|
||||
Reference in new issue
Block a user