Skip to content

Commit 90fc456

Browse files
authored
Merge branch 'main' into unquote-ascii
2 parents 262ee8b + 0e35313 commit 90fc456

21 files changed

Lines changed: 330 additions & 71 deletions

‎.github/workflows/tail-call.yml‎

Lines changed: 2 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -24,17 +24,9 @@ env:
2424

2525
jobs:
2626
macos:
27-
name: ${{ matrix.target }}
28-
runs-on: ${{ matrix.runner }}
27+
name: aarch64-apple-darwin/clang
28+
runs-on: macos-26
2929
timeout-minutes: 60
30-
strategy:
31-
fail-fast: false
32-
matrix:
33-
include:
34-
- target: x86_64-apple-darwin/clang
35-
runner: macos-26-intel
36-
- target: aarch64-apple-darwin/clang
37-
runner: macos-26
3830
steps:
3931
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
4032
with:
@@ -49,7 +41,6 @@ jobs:
4941
- name: Build
5042
run: |
5143
export SDKROOT="$(xcrun --show-sdk-path)"
52-
export PATH="/usr/local/opt/llvm@${{ env.LLVM_VERSION }}/bin:$PATH"
5344
export PATH="/opt/homebrew/opt/llvm@${{ env.LLVM_VERSION }}/bin:$PATH"
5445
CC=clang-${{ env.LLVM_VERSION }} ./configure --with-tail-call-interp
5546
make all --jobs 4

‎.gitignore‎

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -102,6 +102,7 @@ Modules/Setup.config
102102
Modules/Setup.local
103103
Modules/Setup.stdlib
104104
Modules/config.c
105+
Modules/config_bootstrap.c
105106
Modules/ld_so_aix
106107
Programs/_freeze_module
107108
Programs/_testembed

‎Doc/c-api/init_config.rst‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -889,9 +889,9 @@ PyPreConfig
889889
* ``PYMEM_ALLOCATOR_PYMALLOC_DEBUG`` (``6``): :ref:`Python pymalloc
890890
memory allocator <pymalloc>` with :ref:`debug hooks
891891
<pymem-debug-hooks>`.
892-
* ``PYMEM_ALLOCATOR_MIMALLOC`` (``6``): use ``mimalloc``, a fast
892+
* ``PYMEM_ALLOCATOR_MIMALLOC`` (``7``): use ``mimalloc``, a fast
893893
malloc replacement.
894-
* ``PYMEM_ALLOCATOR_MIMALLOC_DEBUG`` (``7``): use ``mimalloc``, a fast
894+
* ``PYMEM_ALLOCATOR_MIMALLOC_DEBUG`` (``8``): use ``mimalloc``, a fast
895895
malloc replacement with :ref:`debug hooks <pymem-debug-hooks>`.
896896
897897

‎Doc/c-api/interp-lifecycle.rst‎

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,6 @@ The following functions can be safely called before Python is initialized:
4848
* :c:func:`Py_GetCopyright`
4949
* :c:func:`Py_GetPlatform`
5050
* :c:func:`Py_GetVersion`
51-
* :c:func:`Py_IsInitialized`
5251

5352
* Utilities:
5453

@@ -491,7 +490,7 @@ deleted. This can be done using interpreter views.
491490
492491
An opaque view of an interpreter.
493492
494-
This is a thread-safe way to access an interpreter that may have be
493+
This is a thread-safe way to access an interpreter that may be
495494
finalizing or already destroyed.
496495
497496
.. versionadded:: 3.15

‎Lib/test/test_except_star.py‎

Lines changed: 82 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -705,6 +705,88 @@ def test_raise_handle_all_raise_two_unnamed(self):
705705
self.assertMetadataEqual(orig, exc.exceptions[0].__context__)
706706
self.assertMetadataEqual(orig, exc.exceptions[1].__context__)
707707

708+
def test_raise_base_exception(self):
709+
class MyBaseException(BaseException):
710+
pass
711+
712+
orig = ExceptionGroup("eg", [ValueError(1), OSError(2)])
713+
try:
714+
try:
715+
raise orig
716+
except* OSError:
717+
raise MyBaseException(3)
718+
except BaseException as e:
719+
exc = e
720+
721+
self.assertIs(type(exc), BaseExceptionGroup)
722+
self.assertEqual(exc.message, "")
723+
self.assertEqual(len(exc.exceptions), 2)
724+
self.assertExceptionIsLike(exc.exceptions[0], MyBaseException(3))
725+
self.assertExceptionIsLike(
726+
exc.exceptions[1], ExceptionGroup("eg", [ValueError(1)]))
727+
728+
self.assertExceptionIsLike(
729+
exc.exceptions[0].__context__,
730+
ExceptionGroup("eg", [OSError(2)]))
731+
732+
self.assertMetadataNotEqual(orig, exc)
733+
self.assertMetadataEqual(orig, exc.exceptions[0].__context__)
734+
735+
def test_raise_handle_all_raise_one_base_exception(self):
736+
class MyBaseException(BaseException):
737+
pass
738+
739+
orig = ExceptionGroup("eg", [TypeError(1), ValueError(2)])
740+
try:
741+
try:
742+
raise orig
743+
except* (TypeError, ValueError):
744+
raise MyBaseException(3)
745+
except BaseException as e:
746+
exc = e
747+
748+
self.assertExceptionIsLike(exc, MyBaseException(3))
749+
750+
self.assertExceptionIsLike(
751+
exc.__context__,
752+
ExceptionGroup("eg", [TypeError(1), ValueError(2)]))
753+
754+
self.assertMetadataNotEqual(orig, exc)
755+
self.assertMetadataEqual(orig, exc.__context__)
756+
757+
def test_raise_handle_all_raise_base_exception_and_exception(self):
758+
class MyBaseException(BaseException):
759+
pass
760+
761+
orig = ExceptionGroup("eg", [TypeError(1), ValueError(2)])
762+
try:
763+
try:
764+
raise orig
765+
except* TypeError:
766+
raise MyBaseException(3)
767+
except* ValueError:
768+
raise SyntaxError(4)
769+
except BaseException as e:
770+
exc = e
771+
772+
self.assertIs(type(exc), BaseExceptionGroup)
773+
self.assertEqual(exc.message, "")
774+
self.assertEqual(len(exc.exceptions), 2)
775+
self.assertExceptionIsLike(exc.exceptions[0], MyBaseException(3))
776+
self.assertExceptionIsLike(exc.exceptions[1], SyntaxError(4))
777+
778+
self.assertExceptionIsLike(
779+
exc.exceptions[0].__context__,
780+
ExceptionGroup("eg", [TypeError(1)]))
781+
782+
self.assertExceptionIsLike(
783+
exc.exceptions[1].__context__,
784+
ExceptionGroup("eg", [ValueError(2)]))
785+
786+
self.assertMetadataNotEqual(orig, exc)
787+
self.assertMetadataEqual(orig, exc.exceptions[0].__context__)
788+
self.assertMetadataEqual(orig, exc.exceptions[1].__context__)
789+
708790

709791
class TestExceptStarRaiseFrom(ExceptStarTest):
710792
def test_raise_named(self):

‎Lib/test/test_free_threading/test_dict.py‎

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -228,6 +228,39 @@ def reader_func():
228228

229229
self.assertEqual(count, 0)
230230

231+
def test_racing_replace_inline_values_and_lookup(self):
232+
# gh-160496: replacing an unmaterialized __dict__ clears inline
233+
# values while attribute lookup can still read them without a lock.
234+
class C:
235+
pass
236+
237+
objects = [C() for _ in range(1000)]
238+
for obj in objects:
239+
obj.x = [0]
240+
241+
# Inline values are invalidated only once per object, so synchronize
242+
# the threads for each fresh instance without accessing its __dict__.
243+
barrier = Barrier(2)
244+
observed = []
245+
246+
def writer():
247+
for obj in objects:
248+
barrier.wait()
249+
obj.__dict__ = {"x": [1]}
250+
barrier.wait()
251+
252+
def reader():
253+
for obj in objects:
254+
barrier.wait()
255+
observed.append(getattr(obj, "x", None))
256+
barrier.wait()
257+
258+
threading_helper.run_concurrently([writer, reader])
259+
for value in observed:
260+
self.assertIn(value, ([0], [1]))
261+
for obj in objects:
262+
self.assertEqual(obj.x, [1])
263+
231264
def test_racing_object_get_set_dict(self):
232265
e = Exception()
233266

‎Lib/test/test_free_threading/test_gc.py‎

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,19 @@ def evil():
9797
thread.start()
9898
thread.join()
9999

100+
def test_running_method_not_collected(self):
101+
class C:
102+
def m(self):
103+
wr = weakref.ref(C.__dict__["m"])
104+
del C.m
105+
gc.collect()
106+
return wr() is not None
107+
108+
def run(self):
109+
return self.m()
110+
111+
self.assertTrue(C().run())
112+
100113
def test_merge_brc_queue_of_detached_thread(self):
101114
# GH-157838: objects queued for merging by a thread that is detached
102115
# (blocked in a lock acquire, sleep, etc.) are merged and freed on its

‎Makefile.pre.in‎

Lines changed: 54 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,13 @@ MODSHARED_NAMES= _MODSHARED_NAMES_
2525
MODDISABLED_NAMES= _MODDISABLED_NAMES_
2626
MODOBJS= _MODOBJS_
2727
MODLIBS= _MODLIBS_
28+
# Objects and libraries of the bootstrap modules (Modules/Setup.bootstrap)
29+
# only. These are the only static modules linked into the build helper
30+
# programs (Programs/_freeze_module, _bootstrap_python), so that other
31+
# builtin modules (Modules/Setup.local, MODULE_BUILDTYPE=static) may depend
32+
# on products of those helpers (frozen modules, getpath).
33+
BOOTSTRAP_MODOBJS= _BOOTSTRAP_MODOBJS_
34+
BOOTSTRAP_MODLIBS= _BOOTSTRAP_MODLIBS_
2835

2936
# === Variables set by configure
3037
VERSION= @VERSION@
@@ -359,11 +366,14 @@ COVERAGE_REPORT_OPTIONS=--rc lcov_branch_coverage=1 --branch-coverage --title "C
359366

360367
##########################################################################
361368
# Modules
362-
MODULE_OBJS= \
363-
Modules/config.o \
369+
MODULE_OBJS_COMMON= \
364370
Modules/main.o \
365371
Modules/gcmodule.o
366372

373+
MODULE_OBJS= \
374+
Modules/config.o \
375+
$(MODULE_OBJS_COMMON)
376+
367377
IO_H= Modules/_io/_iomodule.h
368378

369379
IO_OBJS= \
@@ -614,6 +624,19 @@ LIBRARY_OBJS= \
614624
Modules/getpath.o \
615625
Python/frozen.o
616626

627+
# objects that get linked into the build helper programs
628+
# (Programs/_freeze_module, _bootstrap_python): the core, plus the bootstrap
629+
# modules only (see BOOTSTRAP_MODOBJS). Does not include frozen modules nor
630+
# getpath, which the helpers are used to build.
631+
BOOTSTRAP_LIBRARY_OBJS= \
632+
Modules/getbuildinfo_bootstrap.o \
633+
$(PARSER_OBJS) \
634+
$(OBJECT_OBJS) \
635+
$(PYTHON_OBJS) \
636+
Modules/config_bootstrap.o \
637+
$(MODULE_OBJS_COMMON) \
638+
$(BOOTSTRAP_MODOBJS)
639+
617640
LINK_PYTHON_OBJS=@LINK_PYTHON_OBJS@
618641

619642
##########################################################################
@@ -1613,7 +1636,7 @@ Modules/Setup.bootstrap: $(srcdir)/Modules/Setup.bootstrap.in config.status
16131636
Modules/Setup.stdlib: $(srcdir)/Modules/Setup.stdlib.in config.status
16141637
./config.status $@
16151638

1616-
Makefile Modules/config.c: Makefile.pre \
1639+
Makefile Modules/config.c Modules/config_bootstrap.c: Makefile.pre \
16171640
$(srcdir)/Modules/config.c.in \
16181641
$(MAKESETUP) \
16191642
$(srcdir)/Modules/Setup \
@@ -1624,9 +1647,9 @@ Makefile Modules/config.c: Makefile.pre \
16241647
-s Modules \
16251648
Modules/Setup.local \
16261649
Modules/Setup.stdlib \
1627-
Modules/Setup.bootstrap \
1650+
-b Modules/Setup.bootstrap \
16281651
$(srcdir)/Modules/Setup
1629-
@mv config.c Modules
1652+
@mv config.c config_bootstrap.c Modules
16301653
@echo "The Makefile was updated, you may need to re-run make."
16311654

16321655
.PHONY: regen-test-frozenmain
@@ -1661,9 +1684,9 @@ BOOTSTRAP_HEADERS = \
16611684

16621685
Programs/_bootstrap_python.o: Programs/_bootstrap_python.c $(BOOTSTRAP_HEADERS) $(PYTHON_HEADERS)
16631686

1664-
_bootstrap_python: $(LIBRARY_OBJS_OMIT_FROZEN) Programs/_bootstrap_python.o Modules/getpath.o Modules/Setup.local
1665-
$(LINKCC) $(PY_LDFLAGS_NOLTO) -o $@ $(LIBRARY_OBJS_OMIT_FROZEN) \
1666-
Programs/_bootstrap_python.o Modules/getpath.o $(LIBS) $(MODLIBS) $(SYSLIBS)
1687+
_bootstrap_python: $(BOOTSTRAP_LIBRARY_OBJS) Programs/_bootstrap_python.o Modules/getpath.o Modules/Setup.local
1688+
$(LINKCC) $(PY_LDFLAGS_NOLTO) -o $@ $(BOOTSTRAP_LIBRARY_OBJS) \
1689+
Programs/_bootstrap_python.o Modules/getpath.o $(LIBS) $(BOOTSTRAP_MODLIBS) $(SYSLIBS)
16671690
# Dummy pybuilddir.txt is needed for _bootstrap_python to be runnable
16681691
@echo "none" > ./pybuilddir.txt
16691692

@@ -1681,6 +1704,9 @@ _bootstrap_python: $(LIBRARY_OBJS_OMIT_FROZEN) Programs/_bootstrap_python.o Modu
16811704
#
16821705
# Standard build process:
16831706
# 1) compile minimal core objects for Py_Compile*() and PyMarshal_Write*().
1707+
# Only the bootstrap modules (Modules/Setup.bootstrap) are part of these
1708+
# objects (see BOOTSTRAP_LIBRARY_OBJS), so other builtin modules may
1709+
# depend on the output of the following steps.
16841710
# 2) build Programs/_freeze_module binary.
16851711
# 3) create frozen module headers for importlib and getpath.
16861712
# 4) build _bootstrap_python binary.
@@ -1753,8 +1779,8 @@ Programs/_freeze_module.o: Programs/_freeze_module.c Makefile
17531779

17541780
Modules/getpath_noop.o: $(srcdir)/Modules/getpath_noop.c Makefile
17551781

1756-
Programs/_freeze_module: Programs/_freeze_module.o Modules/getpath_noop.o $(LIBRARY_OBJS_OMIT_FROZEN)
1757-
$(LINKCC) $(PY_CORE_LDFLAGS) -o $@ Programs/_freeze_module.o Modules/getpath_noop.o $(LIBRARY_OBJS_OMIT_FROZEN) $(LIBS) $(MODLIBS) $(SYSLIBS)
1782+
Programs/_freeze_module: Programs/_freeze_module.o Modules/getpath_noop.o $(BOOTSTRAP_LIBRARY_OBJS)
1783+
$(LINKCC) $(PY_CORE_LDFLAGS) -o $@ Programs/_freeze_module.o Modules/getpath_noop.o $(BOOTSTRAP_LIBRARY_OBJS) $(LIBS) $(BOOTSTRAP_MODLIBS) $(SYSLIBS)
17581784

17591785
# We manually freeze getpath.py rather than through freeze_modules
17601786
Python/frozen_modules/getpath.h: Modules/getpath.py $(FREEZE_MODULE_BOOTSTRAP_DEPS)
@@ -1907,11 +1933,24 @@ Modules/getbuildinfo.o: $(PARSER_OBJS) \
19071933
$(MODOBJS) \
19081934
$(DTRACE_OBJS) \
19091935
$(srcdir)/Modules/getbuildinfo.c
1910-
$(CC) -c $(PY_CORE_CFLAGS) \
1936+
$(CC) -c $(PY_CORE_CFLAGS) $(GETBUILDINFO_CFLAGS) \
1937+
-o $@ $(srcdir)/Modules/getbuildinfo.c
1938+
1939+
# Separate object for the build helper programs: it must not depend on
1940+
# $(MODOBJS), which may in turn depend on the helpers' output.
1941+
Modules/getbuildinfo_bootstrap.o: $(PARSER_OBJS) \
1942+
$(OBJECT_OBJS) \
1943+
$(PYTHON_OBJS) \
1944+
$(MODULE_OBJS_COMMON) \
1945+
$(BOOTSTRAP_MODOBJS) \
1946+
$(srcdir)/Modules/getbuildinfo.c
1947+
$(CC) -c $(PY_CORE_CFLAGS) $(GETBUILDINFO_CFLAGS) \
1948+
-o $@ $(srcdir)/Modules/getbuildinfo.c
1949+
1950+
GETBUILDINFO_CFLAGS= \
19111951
-DGITVERSION="\"`LC_ALL=C $(GITVERSION)`\"" \
19121952
-DGITTAG="\"`LC_ALL=C $(GITTAG)`\"" \
1913-
-DGITBRANCH="\"`LC_ALL=C $(GITBRANCH)`\"" \
1914-
-o $@ $(srcdir)/Modules/getbuildinfo.c
1953+
-DGITBRANCH="\"`LC_ALL=C $(GITBRANCH)`\""
19151954

19161955
Modules/getpath.o: $(srcdir)/Modules/getpath.c Python/frozen_modules/getpath.h Makefile $(PYTHON_HEADERS)
19171956
$(CC) -c $(PY_CORE_CFLAGS) -DPYTHONPATH='"$(PYTHONPATH)"' \
@@ -2279,7 +2318,7 @@ regen-slots: Python/slots.toml
22792318
$(PYTHON_FOR_REGEN) $(srcdir)/Tools/build/generate_slots.py \
22802319
--generate-all
22812320

2282-
$(LIBRARY_OBJS) $(MODOBJS) Programs/python.o $(PLATFORM_MAIN_OBJS): $(PYTHON_HEADERS)
2321+
$(LIBRARY_OBJS) $(MODOBJS) Modules/config_bootstrap.o Programs/python.o $(PLATFORM_MAIN_OBJS): $(PYTHON_HEADERS)
22832322

22842323

22852324
######################################################################
@@ -3365,7 +3404,7 @@ clean: clean-profile clean-jit-stencils
33653404
clobber: clean
33663405
-rm -f $(BUILDPYTHON) $(LIBRARY) $(LDLIBRARY) $(DLLLIBRARY) \
33673406
tags TAGS \
3368-
config.cache config.log pyconfig.h Modules/config.c
3407+
config.cache config.log pyconfig.h Modules/config.c Modules/config_bootstrap.c
33693408
-rm -rf build platform
33703409
-rm -rf $(PYTHONFRAMEWORKDIR)
33713410
-rm -rf Platforms/Apple/iOS/Frameworks

‎Misc/NEWS.d/3.15.0a1.rst‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2768,8 +2768,8 @@ Fix the "Invalid error handling" exception in
27682768
.. nonce: Gpr2GB
27692769
.. section: Library
27702770
2771-
+Accept leading zeros in precision and width fields for
2772-
+:class:`~decimal.Decimal` formatting, for example ``format(Decimal(1.25),
2771+
Accept leading zeros in precision and width fields for
2772+
:class:`~decimal.Decimal` formatting, for example ``format(Decimal(1.25),
27732773
'.016f')``.
27742774

27752775
..
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
The build helper programs ``Programs/_freeze_module`` and
2+
``_bootstrap_python`` are now linked only with the modules of
3+
:file:`Modules/Setup.bootstrap`, instead of with every static module. Builtin
4+
modules added via :file:`Modules/Setup.local` or ``MODULE_BUILDTYPE=static``
5+
can now depend on frozen modules or on ``getpath``.

0 commit comments

Comments
 (0)