https://github.com/python/cpython/blob/master/Objects/call.c
の下に関数コールの仕組みやデフォルト引数の扱いの秘密が隠れてそうには思うものの default
で検索しても出てこないし、すぐには分からんなぁ・・・
根性入れて compile して print
デバッグをするなら、Your Guide to the CPython Source Code – Real Python とかかなぁ・・・。と思ったけど、公式 1. Getting Started — Python Developer's Guide を参考に以下のような感じで:
FROM ubuntu:18.04 ENV DEBIAN_FRONTEND noninteractive RUN perl -pi -e 's/# deb-src/deb-src/' /etc/apt/sources.list && \ apt update && apt build-dep -y python3.8 WORKDIR /workdir VOLUME ["/workdir"] CMD ["bash"]
これくらいの Dockerfile
でビルド環境はできるような気がする。(3.9 にするとダメだった。20.04 にすればいけることは確認した)
git clone https://github.com/python/cpython.git
して
$ cpython $ du -h 476M .
だったのでまだマシ・・・。
git checkout v3.8.8 docker run -it --rm -v $PWD:/workdir derwind/python-build bash
で一応は準備ができちゃう的な・・・。
./configure --with-pydebug
make
でビルドは開始する。どれくらいかかるんかな?・・・と思ったら 5 分もかからなかった。すごっ。ビルドに使ったマシンのスペックもあるだろうけど、意外とはやい。*1
https://github.com/python/cpython/blob/v3.8.8/Objects/classobject.c#L106
この辺にログを入れて空の .py を実行させるとめっちゃログが出る。標準モジュールのせいかな?
https://github.com/python/cpython/blob/v3.8.8/Modules/timemodule.c#L68
この辺にログを入れると以下のようになる。一応動いているな・・・
>>> import time >>> time.time() time_time is called 1617383621.7431877
次回以降で CPython インタープリタの中からデフォルト引数の流れを追いかける。但し、断片的に追いかけるので一部推測を交えて手短にやる・・・。
一応のゴールは「デフォルト引数に mutable なオブジェクトを渡すことが嫌われる」ことの裏舞台を下回りから追跡して理解を深めることにある。
*1:Why does cpython use -O3? - Ideas - Discussions on Python.org にあるようにデフォルトでは最適化として -O3 が適用されている。Python 3.8.0b3 からPGOビルドが速くなる - Qiita や UbuntuでPythonをソースからインストール - Qiita で触れられている --enable-optimizations を指定していなくてもである。Issue 38350: ./configure --with-pydebug should use -O0 rather than -Og - Python tracker によると、--with-pydebug を configure に渡すと -Og でのビルドに切り替わる。