【だぶるふりー】
ダブルフリー とは?
💡 同じホテルの部屋を2回チェックアウトしたら、フロントの台帳が壊れた
📌 このページのポイント
- free()を同じポインタで2回呼ぶと起きる
- ヒープの内部メタデータ(空きリスト)が破壊される
- 任意アドレスへの書き込み(Write-What-Where)に発展することがある
- Use-After-Freeと組み合わさったバグとして報告されることも多い
ダブルフリーって、同じメモリを2回解放するってこと?
そうだよ。同じポインタでfree()を2回呼んでしまうバグだね。ヒープを管理しているアロケータは「もう解放したはずの領域をまた解放しようとしている」と混乱してしまうんだ。
混乱するとどうなるの?
ヒープの内部にある「空き領域のリスト(free list)」が壊れてしまうんだよ。そうすると次にmalloc()を呼んだとき、本来返すべきでないアドレスが返ってくることがあるんだ。
それを攻撃者はどう悪用するの?
壊れたfree listを細工することで、次のmalloc()の戻り値を攻撃者が指定したアドレスにできるんだよ。そこにデータを書き込める状態になるから「Write-What-Where」と呼ばれる強力な攻撃プリミティブになるんだ。
Use-After-Freeとの違いは何?
UAFは「解放後にそのポインタを使い続ける」バグで、ダブルフリーは「同じポインタで2回free()を呼んでヒープ管理構造を壊す」バグだよ。でも複雑なコードでは両方が絡まって報告されることも多いんだ。
どうやって防ぐの?
free()した直後にポインタをNULLにする習慣が一番基本的な対策だよ。NULLへのfree()は安全に無視されるからね。C++ではスマートポインタを使うと自動管理できるし、glibcのDouble-Free検出機能やAddressSanitizerでテスト中に発見することもできるんだ。
まとめ:ざっくりこれだけ覚えればOK!
「ダブルフリー」って出てきたら「同じメモリを2回解放してヒープ管理を壊すバグ」と思えればだいたいOK!
📖 おまけ:英語の意味
「Double Free」 = 二重解放
💬 同じメモリ領域をfree()で2回解放してしまうことを指す用語だよ。C言語でポインタ管理を誤ると簡単に起きてしまうんだ。