`trace` function is cleared after `RecursionError` is fired
オープン
まだ誰も着手していません。
interpreter-core
pending
type-bug
- 主要言語
- Python
- スター
- 77.2k
- フォーク
- 35.9k
- PR マージ指標
- PR 指標を取得中
説明
Bug report
Bug description:
I'm using coverage and pytest-cov in CI to measure the line coverage of the unittests. It is achieved by registering a trace function with sys.settrace.
However, after binsecting my unittests, I found that when a RecursionError is raised, the system trace function will be cleared. That will cause a warning emitted by coverage:
~/Projects/cpython/venv/lib/python3.15t/site-packages/coverage/pytracer.py:355: CoverageWarning: Trace function changed, data is likely wrong: None != <bound method PyTracer._trace of <PyTracer at 0x200021dcc20: 2076 data points in 11 files>> (trace-changed)
self.warn(
Reproducible code:
import sys
def tracer(*args, **kwargs):
pass
def factorial(n: int) -> int:
"""Calculate the factorial of a number."""
if n <= 1:
return 1
return n * factorial(n - 1)
sys.settrace(tracer)
assert sys.gettrace() is tracer
sys.setrecursionlimit(64)
assert sys.gettrace() is tracer
try:
_ = factorial(100)
except RecursionError:
pass
assert sys.gettrace() is None
REPL Output:
# Add a code block here, if required
$ python3
Python 3.13.3 (main, Apr 8 2025, 13:54:08) [Clang 16.0.0 (clang-1600.0.26.6)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> import sys
>>> def tracer(*args, **kwargs):
... pass
...
>>> def factorial(n):
... if n <= 1:
... return 1
... return n * factorial(n - 1)
...
>>> sys.settrace(tracer)
>>> sys.gettrace() is tracer
True
>>> sys.setrecursionlimit(64)
>>> _ = factorial(100)
Traceback (most recent call last):
File "<python-input-6>", line 1, in <module>
_ = factorial(100)
File "<python-input-2>", line 4, in factorial
return n * factorial(n - 1)
~~~~~~~~^^^^^^^
File "<python-input-2>", line 4, in factorial
return n * factorial(n - 1)
~~~~~~~~^^^^^^^
File "<python-input-2>", line 4, in factorial
return n * factorial(n - 1)
~~~~~~~~^^^^^^^
[Previous line repeated 51 more times]
File "<python-input-2>", line 1, in factorial
def factorial(n):
RecursionError: maximum recursion depth exceeded
>>> sys.gettrace() is None
True
CPython versions tested on:
CPython main branch
Operating systems tested on:
macOS
コントリビューションガイド
はじめの一歩
- issue を最後まで読み、次にプロジェクトのコントリビューションガイドを読みます。
- 着手することを issue にコメントします — 二人が同じ作業をするのを防げます。
- リポジトリをフォークし、ブランチを切って変更します。
- issue 番号を参照したプルリクエストを送ります。
調査の方向性
提供された reproducer を実行し、再帰的な factorial 呼び出し周辺における sys.settrace、sys.gettrace、RecursionError の挙動を調査します。再帰制限の処理と tracing に関係する CPython の実装パスを追跡します。完了の条件は、RecursionError の後も登録された trace 関数が利用可能なままであり、reproducer に対する回帰テストのカバレッジがあることです。
索引モデルが issue の本文から書いたものです。
評価
- 技術スタック
- python
- 領域
- compilers
- issue の種類
- バグ
- 難易度
- 4/5
- 見積もり時間
- 3〜5日
- 活発さ
- 停滞
- 明瞭さ
- おおむね明確
- 初心者へのやさしさ
- 45/100