
ライセンス:MIT(コード)/ CC BY 4.0(ドキュメント)
防御的セキュリティ研究。標準の PostgreSQL 上で、低権限・インジェクション専用のデータベースロールがトリガーベースの監査者を可逆的に盲目化し、帰属を汚染できるかどうか、そしてどの防御策が実際にそれを阻止するかを検証する。すべては使い捨てのローカル Docker コンテナと完全に合成されたデータ(RFC 5737 ドキュメント用 IP、架空の身元)で実行される。実在のシステム、認証情報、データは一切関与しない。
ラボの概要は self-defeating-audits-lab.md を参照。
PostgreSQL wiki で広くコピーされている「監査トリガー」被害者を構築し、PostgreSQL 14 と 16 にわたって実現可能性マトリクスをセルごとに検証する。各攻撃ベクトルが実際に書き込みの監査を阻止するかどうか、痕跡ゼロで可逆かどうか、そしてどの防御策がそれを無効化するかを、帯域外で測定する。
cd scripts
./00_up.sh 16 # bring up postgres:16-alpine on localhost:55432
./run_matrix.sh 16 # run every matrix cell + defenses -> ../results/RESULTS_pg16.md
docker rm -f sda_pg16 # free the port between versions
./00_up.sh 14
./run_matrix.sh 14 # -> ../results/RESULTS_pg14.md
./teardown.sh # remove all lab containers
Docker が必要。-alpine イメージを使用する(機能的に同一のエンジン)。
この研究はさらに2つのエンジンファミリーで再現されている。MySQL ファミリー(MariaDB、DEFINER トリガーモデル)は scripts/mysql/ 配下:
cd scripts/mysql
./00_up.sh 10.11 && ./run_matrix_mysql.sh 10.11 # -> results/RESULTS_mariadb_10.11.md
docker rm -f sda_maria_10_11 && ./00_up.sh 10.6 && ./run_matrix_mysql.sh 10.6
SQL Server(所有権チェーンモデル)は scripts/mssql/ 配下 — ホストの sqlcmd 経由でローカルの LocalDB インスタンス上で実行される(Docker 不使用。低権限の攻撃者は EXECUTE AS USER の権限借用でモデル化される):
cd scripts/mssql
./run_matrix_mssql.sh # -> results/RESULTS_mssql.md ; then ./teardown.sh
再現性に関する注意(SQL Server)。 Docker エンジンとは異なり、SQL Server の3番目の実行系はホスト依存である:ローカルの SQL Server LocalDB インスタンス上で
sqlcmd経由で実行される(パスはrun_matrix_mssql.shにハードコードされている)。したがって Windows 専用であり、イメージダイジェストに固定できない。低権限の攻撃者はEXECUTE AS USERの権限借用でモデル化される(LocalDB は Windows 認証のみ)。エンジン動作に関する知見(DISABLE は痕跡ゼロ;DDL ガードは DISABLE を見逃す)はセッション種別に依存せず、実際のログインでも成立する。オブジェクト権限に関する知見は権限借用によって忠実に強制される。3つのエンジンの中で最も移植性が低い — 正直に明記しておく。
主要なクロスエンジン結果:search_path シャドウクラス(1A/1B)は MySQL にも SQL Server にも転移しない(search_path が存在しないため)。しかし、トリガー置換、休止状態のバイパス、帰属汚染は転移する。MySQL の DEFINER 権限バインドにより、盲目化はより検出されやすくなる。SQL Server は PostgreSQL と同様にバイト完全な復元が可能であり、さらに自前の DDL 防御が見逃す痕跡ゼロの DISABLE TRIGGER プリミティブを備える。3エンジン全体の比較は FINDINGS.md に記載。
CREATE SCHEMA できない)。「pg_catalog が優先されるから」ではない。すでに書き込み可能な public への仕込みはシャドウが成立する:1S(同一シグネチャ、スキーマ順序)と 1T(完全一致のオーバーロードが pg_catalog が先でも 組み込み関数に勝つ — 型特異性を切り分ける)はどちらも盲目化する(ペイロードは NULL 化)。row_to_json オーバーロード — public が書き込み可能でトリガーの search_path が未固定の場合、監査者を盲目化する。標準の PostgreSQL ≤14 では到達可能;15+ では設定ミスが前提。 search_path を固定すれば、どの環境でも無効化できる。pgaudit/log_statement)+ ハッシュチェーン型シンクが、この攻撃セットを封じる防御策である。匿名化/合成データを用いたローカルラボの標準 PostgreSQL 上で再現した。攻撃 SQL はここで構築したラボのスキーマに限定されている。これは実現可能性/防御の研究であり、武器化されたペイロードではない。基礎となるプリミティブはすでに公開されている(CVE-2018-1058;SECURITY DEFINER の search_path 昇格)— 貢献はその組み合わせと防御評価にある。実在のシステムは特定されていない。
| パス | 内容 |
|---|
scripts/00_up.sh | バージョン固定の使い捨てコンテナ(PostgreSQL) |
scripts/mysql/ | MySQL ファミリー(MariaDB)の被害者、攻撃、防御、オーケストレータ |
scripts/mssql/ | SQL Server(LocalDB)の被害者、攻撃、防御、オーケストレータ |
results/RESULTS_mariadb_*.md | MySQL ファミリーの実現可能性 + 防御マトリクス |
results/RESULTS_mssql.md | SQL Server の実現可能性 + 防御マトリクス |
scripts/10_victim.sql | wiki パターンの監査被害者(SECURITY DEFINER トリガー);調整項目:pub_create、pin_path、app_owns |
scripts/20_attacks.sql | すべての攻撃ベクトル(1A/1B/1C、GUC 休止状態、帰属汚染)、セルごとに 1 つの \if ガード |
scripts/30_defenses.sql | DDL イベントトリガーガード + ハッシュチェーン型の追記専用シンク |
scripts/40_snapshot.sql | RQ2 オブジェクト差分用のカタログスナップショット |
scripts/run_matrix.sh | オーケストレータ:各セルを構築・測定し、results/RESULTS_pg<VER>.md を書き出す |
scripts/teardown.sh | コンテナの削除 |
results/RESULTS_pg14.md, results/RESULTS_pg16.md | バージョンごとの実現可能性 + 防御マトリクス(記入済み) |
results/_evidence_pg*.log, results/_snap_1C_*.txt | 生のコマンド/出力エビデンス |
FINDINGS.md | 平易な英語による RQ1–RQ5 の判定、防御×攻撃マトリクス、新規性の位置づけ、アブストラクト |