24/7 twenty-four seven

iOS/OS X application programing topics.

二重解放 (double free) や 解放済みオブジェクトへのアクセス (EXC_BAD_ACCESS) によるクラッシュを Instruments を使って調べる

iPhone アプリケーションのプログラミングでは、メモリ管理に注意する必要があります。
特に解放済みのオブジェクトをさらに解放してしまったり(二重解放)、解放済みのオブジェクトを操作しようとした場合は即座にアプリがクラッシュしてしまいます。


このようなメモリ関連のバグによるクラッシュの場合、何も残さずに突然終了してしまうことが多いため、原因の究明が困難です。


そんなメモリ管理のバグを Instruments を使って少し簡単に調査する方法を紹介します。
残念ながら、シミュレータでしが機能しないのですが、それでも原因の解明が簡単になる場合が結構あります。


下記のサイトでは、動画と画像でさらに詳しく解説されているので、そちらも参考にしてください。
iPhone Memory Debugging with NSZombie and Instruments — markj.net

プロジェクトをビルドして、「実行」>「パフォーマンスツールを使って実行」>「Object Allocations」を選択します。

Instruments の設定を変更するため、「Stop」を押して、いったん停止します。

「ObjectAlloc」の右側にある「i」マークのボタンを押して「Record reference counts」と「Enable NSZombie detection」を有効にします。

「Record reference counts」はオブジェクトごとの参照カウンタの記録、「Enable NSZombie detection」は dealloc されたオブジェクトを実際には解放せずに、ゾンビオブジェクトとして扱う機能になります。
実際にはオブジェクトを解放しないので、クラッシュ時に原因の追跡が可能になります。

設定を有効にしたら、「Record」ボタンを押してアプリケーションを再実行します。

アプリケーションを操作してクラッシュを再現します。
すると、(メモリ関連のバグの場合)下記のように Instruments にクラッシュが報告されます。

ここで吹き出しの右下にある矢印ボタンを押すと、原因となったオブジェクトの状態の経過と、参照カウンタが表示されます。

さらに、該当する行が自分で書いたコードの場合、行をダブルクリックすることで、コードの表示にジャンプします。


以上です。
コードが大きくなってくると、メモリ関連の異常終了はなかなか原因を特定することが難しいですが、上記の方法にてデバッグすることで少し簡単になることがあると思います。