mirror of
https://github.com/RustPython/RustPython.git
synced 2026-10-28 18:59:04 +08:00
* vm: drop trailing space from RecursionError text Format Python-limit and native-stack RecursionError messages through one helper so empty context is not a trailing space or an empty string. Assisted-by: Grok 4.6 * test: deepen nested hash snippets for release stack frames The cold RecursionError helper thins with_recursion's hot frame, so 100_000 nested hashes no longer trip the native stack guard in release. Assisted-by: Grok 4.6 * vm: let RecursionError callers own the where-clause space The helper concatenates an empty suffix or one that already starts with a space. Call sites supply that space. Assisted-by: Grok 4.6
76 lines
1.5 KiB
Python
76 lines
1.5 KiB
Python
from testutils import assert_raises
|
|
|
|
|
|
class Foo(object):
|
|
pass
|
|
|
|
|
|
Foo.__repr__ = Foo.__str__
|
|
|
|
foo = Foo()
|
|
# Since the default __str__ implementation calls __repr__ and __repr__ is
|
|
# actually __str__, str(foo) should raise a RecursionError.
|
|
assert_raises(RecursionError, str, foo)
|
|
|
|
|
|
# A __call__ that is the object being called dispatches through the call slot
|
|
# again, and none of that pushes a Python frame.
|
|
|
|
|
|
class Caller:
|
|
pass
|
|
|
|
|
|
caller = Caller()
|
|
Caller.__call__ = caller
|
|
assert_raises(RecursionError, caller)
|
|
|
|
|
|
# The same shape through the descriptor protocol: resolving the attribute
|
|
# fetches __get__, which is the descriptor itself.
|
|
|
|
|
|
class Descr:
|
|
pass
|
|
|
|
|
|
descr = Descr()
|
|
Descr.__get__ = descr
|
|
Descr.x = descr
|
|
try:
|
|
descr.x
|
|
except (RecursionError, TypeError):
|
|
# RecursionError here, TypeError from the call of a non-callable elsewhere
|
|
pass
|
|
else:
|
|
raise AssertionError("descr.x should not resolve")
|
|
|
|
|
|
def recurse():
|
|
recurse()
|
|
|
|
|
|
try:
|
|
recurse()
|
|
except RecursionError as e:
|
|
msg = str(e)
|
|
assert msg, f"empty RecursionError message: {e!r}"
|
|
assert not msg.endswith(" "), f"trailing space in RecursionError: {e!r}"
|
|
|
|
import sys
|
|
|
|
prev_limit = sys.getrecursionlimit()
|
|
try:
|
|
sys.setrecursionlimit(50)
|
|
try:
|
|
recurse()
|
|
except RecursionError as e:
|
|
assert str(e) == "maximum recursion depth exceeded", (
|
|
f"unexpected message: {e!r}"
|
|
)
|
|
assert e.args == ("maximum recursion depth exceeded",), (
|
|
f"unexpected args: {e.args!r}"
|
|
)
|
|
finally:
|
|
sys.setrecursionlimit(prev_limit)
|