Skip to content

Commit 88d48f6

Browse files
authored
Merge branch 'main' into shelve-clear
2 parents 0353d56 + c2b1689 commit 88d48f6

25 files changed

+177
-109
lines changed

Include/cpython/interpreteridobject.h

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
#ifndef Py_CPYTHON_INTERPRETERIDOBJECT_H
2+
# error "this header file must not be included directly"
3+
#endif
4+
5+
/* Interpreter ID Object */
6+
7+
PyAPI_DATA(PyTypeObject) PyInterpreterID_Type;
8+
9+
PyAPI_FUNC(PyObject *) PyInterpreterID_New(int64_t);
10+
PyAPI_FUNC(PyObject *) PyInterpreterState_GetIDObject(PyInterpreterState *);
11+
PyAPI_FUNC(PyInterpreterState *) PyInterpreterID_LookUp(PyObject *);

Include/cpython/pylifecycle.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,3 +77,7 @@ typedef struct {
7777
PyAPI_FUNC(PyStatus) Py_NewInterpreterFromConfig(
7878
PyThreadState **tstate_p,
7979
const PyInterpreterConfig *config);
80+
81+
typedef void (*atexit_datacallbackfunc)(void *);
82+
PyAPI_FUNC(int) PyUnstable_AtExit(
83+
PyInterpreterState *, atexit_datacallbackfunc, void *);

Include/cpython/pystate.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
PyAPI_FUNC(int) _PyInterpreterState_RequiresIDRef(PyInterpreterState *);
99
PyAPI_FUNC(void) _PyInterpreterState_RequireIDRef(PyInterpreterState *, int);
1010

11+
PyAPI_FUNC(PyObject *) PyUnstable_InterpreterState_GetMainModule(PyInterpreterState *);
1112

1213
/* State unique per thread */
1314

Include/internal/pycore_interp.h

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -238,9 +238,6 @@ extern int _PyInterpreterState_IDInitref(PyInterpreterState *);
238238
extern int _PyInterpreterState_IDIncref(PyInterpreterState *);
239239
extern void _PyInterpreterState_IDDecref(PyInterpreterState *);
240240

241-
// Export for '_xxsubinterpreters' shared extension
242-
PyAPI_FUNC(PyObject*) _PyInterpreterState_GetMainModule(PyInterpreterState *);
243-
244241
extern const PyConfig* _PyInterpreterState_GetConfig(PyInterpreterState *interp);
245242

246243
/* Get a copy of the current interpreter configuration.

Include/internal/pycore_interp_id.h

Lines changed: 0 additions & 28 deletions
This file was deleted.

Include/interpreteridobject.h

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
#ifndef Py_INTERPRETERIDOBJECT_H
2+
#define Py_INTERPRETERIDOBJECT_H
3+
4+
#ifdef __cplusplus
5+
extern "C" {
6+
#endif
7+
8+
#ifndef Py_LIMITED_API
9+
# define Py_CPYTHON_INTERPRETERIDOBJECT_H
10+
# include "cpython/interpreteridobject.h"
11+
# undef Py_CPYTHON_INTERPRETERIDOBJECT_H
12+
#endif
13+
14+
#ifdef __cplusplus
15+
}
16+
#endif
17+
#endif /* !Py_INTERPRETERIDOBJECT_H */

Lib/test/test_capi/check_config.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ def import_singlephase():
1212
try:
1313
import _testsinglephase
1414
except ImportError:
15-
sys.modules.pop('_testsinglephase')
15+
sys.modules.pop('_testsinglephase', None)
1616
return False
1717
else:
1818
del sys.modules['_testsinglephase']

Lib/test/test_clinic.py

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -679,6 +679,32 @@ def test_return_converter(self):
679679
""")
680680
self.assertIsInstance(function.return_converter, clinic.int_return_converter)
681681

682+
def test_return_converter_invalid_syntax(self):
683+
stdout = self.parse_function_should_fail("""
684+
module os
685+
os.stat -> invalid syntax
686+
""")
687+
expected_error = "Badly formed annotation for os.stat: 'invalid syntax'"
688+
self.assertIn(expected_error, stdout)
689+
690+
def test_legacy_converter_disallowed_in_return_annotation(self):
691+
stdout = self.parse_function_should_fail("""
692+
module os
693+
os.stat -> "s"
694+
""")
695+
expected_error = "Legacy converter 's' not allowed as a return converter"
696+
self.assertIn(expected_error, stdout)
697+
698+
def test_unknown_return_converter(self):
699+
stdout = self.parse_function_should_fail("""
700+
module os
701+
os.stat -> foooooooooooooooooooooooo
702+
""")
703+
expected_error = (
704+
"No available return converter called 'foooooooooooooooooooooooo'"
705+
)
706+
self.assertIn(expected_error, stdout)
707+
682708
def test_star(self):
683709
function = self.parse_function("""
684710
module os

Lib/test/test_import/__init__.py

Lines changed: 37 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -97,7 +97,6 @@ def require_frozen(module, *, skip=True):
9797
def require_pure_python(module, *, skip=False):
9898
_require_loader(module, SourceFileLoader, skip)
9999

100-
101100
def remove_files(name):
102101
for f in (name + ".py",
103102
name + ".pyc",
@@ -147,19 +146,34 @@ def _ready_to_import(name=None, source=""):
147146
del sys.modules[name]
148147

149148

150-
def requires_subinterpreters(meth):
151-
"""Decorator to skip a test if subinterpreters are not supported."""
152-
return unittest.skipIf(_interpreters is None,
153-
'subinterpreters required')(meth)
149+
if _testsinglephase is not None:
150+
def restore__testsinglephase(*, _orig=_testsinglephase):
151+
# We started with the module imported and want to restore
152+
# it to its nominal state.
153+
_orig._clear_globals()
154+
_testinternalcapi.clear_extension('_testsinglephase', _orig.__file__)
155+
import _testsinglephase
154156

155157

156158
def requires_singlephase_init(meth):
157159
"""Decorator to skip if single-phase init modules are not supported."""
160+
if not isinstance(meth, type):
161+
def meth(self, _meth=meth):
162+
try:
163+
return _meth(self)
164+
finally:
165+
restore__testsinglephase()
158166
meth = cpython_only(meth)
159167
return unittest.skipIf(_testsinglephase is None,
160168
'test requires _testsinglephase module')(meth)
161169

162170

171+
def requires_subinterpreters(meth):
172+
"""Decorator to skip a test if subinterpreters are not supported."""
173+
return unittest.skipIf(_interpreters is None,
174+
'subinterpreters required')(meth)
175+
176+
163177
class ModuleSnapshot(types.SimpleNamespace):
164178
"""A representation of a module for testing.
165179
@@ -1962,6 +1976,20 @@ def test_isolated_config(self):
19621976
with self.subTest(f'{module}: strict, fresh'):
19631977
self.check_compatible_fresh(module, strict=True, isolated=True)
19641978

1979+
@requires_subinterpreters
1980+
@requires_singlephase_init
1981+
def test_disallowed_reimport(self):
1982+
# See https://github.com/python/cpython/issues/104621.
1983+
script = textwrap.dedent('''
1984+
import _testsinglephase
1985+
print(_testsinglephase)
1986+
''')
1987+
interpid = _interpreters.create()
1988+
with self.assertRaises(_interpreters.RunFailedError):
1989+
_interpreters.run_string(interpid, script)
1990+
with self.assertRaises(_interpreters.RunFailedError):
1991+
_interpreters.run_string(interpid, script)
1992+
19651993

19661994
class TestSinglePhaseSnapshot(ModuleSnapshot):
19671995

@@ -2017,6 +2045,10 @@ def setUpClass(cls):
20172045
# Start fresh.
20182046
cls.clean_up()
20192047

2048+
@classmethod
2049+
def tearDownClass(cls):
2050+
restore__testsinglephase()
2051+
20202052
def tearDown(self):
20212053
# Clean up the module.
20222054
self.clean_up()

Lib/test/test_sys.py

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,12 +14,21 @@
1414
from test.support.script_helper import assert_python_ok, assert_python_failure
1515
from test.support import threading_helper
1616
from test.support import import_helper
17-
from test.support import interpreters
17+
try:
18+
from test.support import interpreters
19+
except ImportError:
20+
interpreters = None
1821
import textwrap
1922
import unittest
2023
import warnings
2124

2225

26+
def requires_subinterpreters(meth):
27+
"""Decorator to skip a test if subinterpreters are not supported."""
28+
return unittest.skipIf(interpreters is None,
29+
'subinterpreters required')(meth)
30+
31+
2332
# count the number of test runs, used to create unique
2433
# strings to intern in test_intern()
2534
INTERN_NUMRUNS = 0
@@ -700,6 +709,7 @@ def __hash__(self):
700709

701710
self.assertRaises(TypeError, sys.intern, S("abc"))
702711

712+
@requires_subinterpreters
703713
def test_subinterp_intern_dynamically_allocated(self):
704714
global INTERN_NUMRUNS
705715
INTERN_NUMRUNS += 1
@@ -715,6 +725,7 @@ def test_subinterp_intern_dynamically_allocated(self):
715725
assert id(t) != {id(t)}, (id(t), {id(t)})
716726
'''))
717727

728+
@requires_subinterpreters
718729
def test_subinterp_intern_statically_allocated(self):
719730
# See Tools/build/generate_global_objects.py for the list
720731
# of strings that are always statically allocated.

0 commit comments

Comments
 (0)