リファレンスの生成
リファレンスの生成は次のように行っている。Reference NO_INSTRUMENT new_Reference(void* object, void (*destructor)(void* object)) { Reference this = (Reference)malloc(sizeof(struct Reference)); if (this != null) { this->object = object; this->frames = frames; this->referenceCounter = 1; this->destructor = destructor; } add(this); return this; }ヒープ領域からメモリを割り当て、オブジェクトとデストラクタ、framesを記憶し、参照カウンタは1で初期化する。
この実験コードでの framesはグローバル変数であり、複数スレッドに対応していないが、マルチスレッド化するときには framesは TLSに配置される予定である。その場合、Referenceがどの framesに対応しているか素早く探すためのものである。
TLSからキーで検索するならこれは不要である。
つぎに生成したリファレンスを framesに登録するために add関数を呼ぶ。
メモリ割り当てに失敗したときにも addししまうのは暫定のためである。
再帰呼び出しされる関数の中でリファレンスが作られるなら、単純に if文の中に入れれば良いと言うわけにはいかない(復帰時に他の階層のリファレンスを破棄する恐れがある)ので、何らかの配慮が必要になる。
その add関数はつぎの通り。
private void add(Reference r) { int top = ArrayList_size(frames) - 1; Frame frame = ArrayList_get(frames, top); ArrayList_add(frame->references, r); }
framesリストの先頭にある frameリストを取り出す。
frameリストにリファレンスを追加する。
framesと frameの各リストの構造を(その2)の例題 testAutoCollectを例に図式化すると次のようになる。
洗濯機が貰えるなら僕らもノーベル賞取ろうよ。