概要

バッファオーバーフロー(BOF:Buffer Overflow)は、プログラムが確保したバッファの範囲を超えてデータを書き込むことで、隣接するメモリ領域を上書きする脆弱性です。攻撃者が戻りアドレスを書き換えることで任意コード実行(RCE)が可能になります。C/C++など手動メモリ管理言語で特に問題となり、SC試験の午前Iでは定番の出題テーマです。

仕組みと動作原理

スタックバッファオーバーフロー

スタックには関数の局所変数・引数・戻りアドレスが積まれています。

スタックの配置(低アドレス → 高アドレス):
[バッファ(8バイト確保)] [その他変数] [SFP] [リターンアドレス]

通常の入力("ABCD"):
[A][B][C][D][ ][ ][ ][ ] [SFP] [正常なリターンアドレス]

悪意ある入力(20バイト):
[A]...[A][A][A][A] [A][A][A][A] [攻撃者のアドレス]
  バッファ溢れ     SFP上書き   リターンアドレス上書き

リターンアドレスを書き換えることで、関数の返り先を攻撃者のコード(シェルコード)に誘導できます。

スタックバッファオーバーフロー攻撃の流れ
1
確保したバッファを超える悪意ある入力を送信
2
バッファが溢れてSFPを上書き
3
リターンアドレスを攻撃者のアドレスに上書き
4
関数終了時に攻撃者のシェルコードへ制御が移る
任意コード実行(RCE)

ヒープバッファオーバーフロー

動的メモリ(malloc/new で確保)の範囲を超えた書き込みです。ヒープ管理構造を破壊し、任意コード実行に至るケースがあります。Use-After-Free(解放済みメモリへのアクセス)も関連した脆弱性です。

整数オーバーフロー

整数型の最大値を超えた計算結果がラップアラウンド(折り返し)することで、バッファサイズ計算が誤り、BOFが発生するケースがあります。

主な防御技術

OSレベルの防御

技術仕組み効果
ASLR(Address Space Layout Randomization)スタック・ヒープ・ライブラリのアドレスをランダム化リターンアドレスの予測を困難にする
DEP/NX(Data Execution Prevention / No eXecute)データ領域のコード実行を禁止スタック上のシェルコード実行を防止
Stack Canary関数呼び出し時にリターンアドレス直前に乱数(カナリア値)を配置。関数返り時に値が変わっていたらBOFを検出リターンアドレス書き換えを検出
CFI(Control Flow Integrity)関数の呼び出し先を正規のアドレスに制限ROP攻撃を緩和

コードレベルの防御

技術説明
境界チェックgets()fgets() など境界チェックありの関数を使用
メモリ安全言語の採用Rust・Go・Javaなど境界チェックを自動で行う言語を使用
静的解析(SAST)コンパイル前にBOFパターンを検出するツールを使用
ファジング大量のランダム入力でBOFを発見するテスト手法

高度な攻撃技法(ASLRとDEP回避)

技法仕組み
ROP(Return-Oriented Programming)DEPがあってもすでにメモリ上の正規コード断片(ガジェット)を繋いで任意処理を実行
Heap Spray大量のメモリにシェルコードを配置してASLRを確率的に回避
Ret2libclibc の system() 関数を呼び出してシェルを起動

メモリ安全性の現代的な議論

2023年にNSA・CISAが「メモリ安全言語(Rust・C#・Java・Go等)へ移行すること」を推奨するガイダンスを発表しました。Microsoftのセキュリティ脆弱性の約70%はメモリ安全性の問題に起因するとされています。

SC試験での頻出ポイント

  • スタックBOFの原理:バッファを溢れさせてリターンアドレスを上書きし、任意コードを実行
  • ASLRの目的:メモリアドレスをランダム化して攻撃コードのアドレス予測を困難にする
  • DEP/NXの目的:データ領域のコード実行を禁止してスタック上のシェルコード実行を防ぐ
  • カナリア値の役割:リターンアドレス手前に置いてBOFを検出する番人(canary=炭鉱のカナリア)
  • ROP攻撃とは:DEPを回避するためにすでにメモリ上の正規コード断片を連鎖的に実行する高度な攻撃

よくある誤問・ひっかけパターン

誤り① 「ASLRだけでBOFは防げる」→ 。ASLRはアドレス予測を困難にするだけで、BOF自体を防ぎません。Heap Sprayなどで回避されることもあります。

誤り② 「Java・Pythonではバッファオーバーフローは発生しない」→ 基本的に正しい。ただしJVMやインタープリタ自体がC/C++で書かれているため、そこに脆弱性があれば影響を受ける可能性があります。

誤り③ 「DEPを有効にすればROP攻撃を防げる」→ 。ROP攻撃はDEPを前提として考案された回避技法であり、DEPだけでは防げません。

関連用語

重要キーワード

用語説明
バッファオーバーフローバッファの境界を超えたデータ書き込みによる隣接メモリの上書き
リターンアドレス関数の処理が終わった後に実行を再開するアドレス
ASLRスタック・ヒープ・ライブラリのメモリアドレスをランダム化する防御技術
DEP/NXデータ領域でのコード実行を禁止するCPU・OS機能
Stack Canary関数返り時にリターンアドレス改ざんを検出するためのランダム値
ROP既存コード断片を繋いでDEPを回避する高度な攻撃技法