コードリーディング観察日記

以前コードリーディングの方法を聞かれて「僕、全然読めないよ」と答えたんだけど、そういう解釈はさておき客観的事実としては30分の空き時間で「Pythonクラスのメソッド名解決順序」に書いてあるようなことを調べられたわけなので、そのプロセスがどうであったか忘れないうちに観察日記をつけておく。

観察日記

  • (調べたい内容が、Pythonのリファレンスマニュアルに書いてあった気がしない)
  • Pythonの処理系で対話的に実行して、挙動を確認。「__bases__を書き換えた時に__mro__を更新するはずだ」と考える
  • ソースコードは既にダウンロード済み(~/src/にソースを読もうと思ったもののソースコードは入れっぱなしになっている)
  • Objects/classobject.cを開く。__bases__で検索する。set_basesって関数を見つける。読む。期待に反して__mro__の更新が行われていない。おかしい。
  • ./configure --with-pydebug してデバッグ情報付きのバイナリを作る。set_basesにブレークポイントをつけて実行。set_basesが呼ばれると考えたPythonコードを実行してもブレークされない。期待に反して呼ばれてない。
  • ソースルートで ack set_bases する。typeobject.cにtype_set_basesなんてのがあるじゃん!そうか、新スタイルのクラスはtypeobject.cか。
  • ack type_set_bases する。type_set_basesを読む。mroって単語が出てくるところだけ流し読みする。
  • r = mro_subclasses(type, temp);が見つかる。
  • mro_subclassesが自分自身とサブクラスのmroを書き換えるかなと期待したが、期待に反してmro_subclassesの中ではサブクラスをたどりながらmro_internalを呼び出すだけ。
  • mro_internalがmroを書き換える処理なのか、と思ってtype_set_basesを読みなおしてみると、mro_internalを読み落としていたのが見つかった。
  • 今思えばmroで検索してハイライトしとけよ自分
  • mro_internalを読んでみたらmro_implementationってのを読んでる。mro_implementationを読んだらさがしていたものはこれっぽい。調査終了。
  • PyTypeObjectの定義を書いておこうと考える。Include/type...h を開こうとしたがそんな名前のファイルはない。ack PyTypeObjectする。いっぱい出すぎる。そりゃそうだ。ack PyTypeObject Include/*.hする。object.hのなかにあった。

使用したツール

  • gdb
    • b(reakepoint)とr(un)しか使ってない
  • ack
  • emacs
    • タグジャンプ使いこなせてない…。
    • インクリメンタルサーチ(Ctrl-sやCtrl-r)と、行番号ジャンプ(僕はCtrl-lにバインドしている)で。
    • あっ、EmacsでのM-x pdbもこの前教えてもらったのに使うの忘れてた。生でgdbつかってたや。

まとめ

やっぱりほとんど読んでない。100行未満。

もっと手練の人の観察日記を読みたい!