削除ファイル復元のためのMFT分析
概要
NTFSマスターファイルテーブル($MFT)は、NTFSボリューム上のすべてのファイルとディレクトリの中心的なメタデータリポジトリです。各ファイルは少なくとも1つの1024バイトのMFTレコードで表され、$STANDARD_INFORMATION(タイムスタンプ、アクセス権限)、$FILE_NAME(ファイル名、親ディレクトリ、タイムスタンプ)、$DATA(ファイル内容またはクラスタ実行ポインタ)などの属性が含まれます。ファイルが削除されると、そのMFTレコードは非アクティブとしてマークされます(InUseフラグがクリアされる)が、新しいファイルによってエントリが再割り当てされるまでメタデータは残り続けます。この永続性により、MFT分析は削除ファイルの証拠復元、ファイルシステムタイムラインの再構築、およびタイムスタンプ操作(timestomping)などのアンチフォレンジックアクティビティの検出のための主要な手法となっています。
使用タイミング
- 削除ファイル復元のためにMFT分析を必要とするセキュリティインシデントを調査する場合
- このドメイン向けの検知ルールや脅威ハンティングクエリを構築する場合
- SOCアナリストがこの分析タイプのための構造化された手順を必要とする場合
- 関連する攻撃テクニックに対するセキュリティ監視カバレッジを検証する場合
前提条件
- フォレンジックディスクイメージ(E01、raw/dd、VMDK、またはVHDX形式)
- MFTECmd(Eric Zimmerman)またはanalyzeMFT(Pythonベース)
- FTK Imager、Arsenal Image Mounter、または同様のイメージマウントツール
- Timeline ExplorerまたはExcel(CSV分析用)
- Python 3.8以上(カスタム分析スクリプト用)
- NTFSファイルシステム内部構造の理解
MFT構造とレコードレイアウト
MFTレコードヘッダー
各MFTレコードはシグネチャ「FILE」(0x46494C45)で始まり、以下を含みます:
| オフセット | サイズ | フィールド |
|---|---|---|
| 0x00 | 4バイト | シグネチャ(「FILE」) |
| 0x04 | 2バイト | 更新シーケンスへのオフセット |
| 0x06 | 2バイト | 更新シーケンスのサイズ |
| 0x08 | 8バイト | $LogFileシーケンス番号 |
| 0x10 | 2バイト | シーケンス番号 |
| 0x12 | 2バイト | ハードリンク数 |
| 0x14 | 2バイト | 最初の属性へのオフセット |
| 0x16 | 2バイト | フラグ(0x01 = InUse、0x02 = ディレクトリ) |
| 0x18 | 4バイト | MFTレコードの使用サイズ |
| 0x1C | 4バイト | MFTレコードの割り当てサイズ |
| 0x20 | 8バイト | ベースファイルレコード参照 |
| 0x28 | 2バイト | 次の属性ID |
主要なMFT属性
| タイプID | 名前 | 説明 |
|---|---|---|
| 0x10 | $STANDARD_INFORMATION | タイムスタンプ、フラグ、所有者ID、セキュリティID |
| 0x30 | $FILE_NAME | ファイル名、親MFT参照、タイムスタンプ |
| 0x40 | $OBJECT_ID | ファイルの一意のGUID |
| 0x50 | $SECURITY_DESCRIPTOR | ACLアクセス権限 |
| 0x60 | $VOLUME_NAME | ボリュームラベル(ボリュームメタデータファイルのみ) |
| 0x80 | $DATA | ファイル内容(700バイト未満の場合は常駐)またはクラスタ実行リスト |
| 0x90 | $INDEX_ROOT | ディレクトリ用のB-treeインデックスルート |
| 0xA0 | $INDEX_ALLOCATION | 大規模ディレクトリ用のB-treeインデックスエントリ |
| 0xB0 | $BITMAP | インデックスまたはMFTの割り当てビットマップ |
削除ファイル復元テクニック
テクニック1:MFTECmdによるMFTレコード分析
# KAPEまたはFTK Imagerを使用してフォレンジックイメージから$MFTを抽出
# MFTECmdで$MFTを解析
MFTECmd.exe -f "C:\Evidence\$MFT" --csv C:\Output --csvf mft_full.csv
# Timeline Explorerで削除ファイルをフィルタリング(InUse = FALSE)
# InUse列がFalseであるエントリを探す
CSV出力での削除ファイルの識別方法:
InUse= Falseは削除または再割り当てされたレコードを示すParentPathは削除前の元のファイル場所を示すFileSizeは元のサイズを示す(復元可能な場合がある)$STANDARD_INFORMATIONと$FILE_NAME属性のタイムスタンプは保持される
テクニック2:USNジャーナル($UsnJrnl:$J)分析
USNジャーナルは、NTFSボリューム上のすべてのファイル変更(作成、削除、名前変更、データ変更イベント)を記録します。
# MFTECmdでUSNジャーナルを解析
MFTECmd.exe -f "C:\Evidence\$J" --csv C:\Output --csvf usn_journal.csv
# 削除証拠に関する主要なUSN理由コード:
# USN_REASON_FILE_DELETE = 0x00000200
# USN_REASON_CLOSE = 0x80000000
# USN_REASON_RENAME_OLD_NAME = 0x00001000
# USN_REASON_RENAME_NEW_NAME = 0x00002000
テクニック3:$LogFileトランザクション分析
$LogFileはNTFSトランザクションレコードを保存しており、USNジャーナルが循環された後でもファイル操作を明らかにできます。
# LogFileParserで$LogFileを解析
LogFileParser.exe -l "C:\Evidence\$LogFile" -o C:\Output
# ファイル削除を示すREDOおよびUNDO操作を探す:
# - DeallocateFileRecordSegment
# - DeleteAttribute
# - UpdateResidentValue(InUseフラグのクリア)
テクニック4:MFTスラックスペース分析
MFTスラックスペースは、MFTレコードの使用部分の終わりから割り当てられた1024バイトの終わりまでの間に存在します。この領域には、以前のファイルレコードの残骸が含まれている可能性があります。
import struct
def parse_mft_slack(mft_path: str, output_path: str):
"""削除ファイルの残骸を抽出・分析するためにMFTスラックスペースを解析します。"""
with open(mft_path, "rb") as f:
record_size = 1024
record_num = 0
slack_findings = []
while True:
record = f.read(record_size)
if len(record) < record_size:
break
# FILEシグネチャを確認
if record[:4] != b"FILE":
record_num += 1
continue
# オフセット0x18から使用サイズを取得
used_size = struct.unpack("<I", record[0x18:0x1C])[0]
if used_size < record_size:
slack = record[used_size:]
# スラックに読み取り可能な文字列または属性ヘッダーが含まれているか確認
if any(c > 0x20 and c < 0x7F for c in slack[:50]):
slack_findings.append({
"record": record_num,
"used_size": used_size,
"slack_size": record_size - used_size,
"slack_preview": slack[:100].hex()
})
record_num += 1
return slack_findings
関連アーティファクトとの相関
MFTと$Recycle.Binのクロスリファレンス
# RBCmdでリサイクルビンを解析
RBCmd.exe -d "C:\Evidence\$Recycle.Bin" --csv C:\Output --csvf recycle_bin.csv
# 相関:$Iファイルには元のパスと削除タイムスタンプが含まれる
# $RファイルからMFTエントリ番号を元のMFTレコードにマッチング
MFTとボリュームシャドウコピーのクロスリファレンス
# ボリュームシャドウコピーを一覧表示
vssadmin list shadows
# シャドウコピーをマウントし、それぞれから$MFTを抽出
# シャドウコピー間でMFTレコードを比較し、経時的なファイル変更を追跡
フォレンジック価値
- 削除ファイルのメタデータ復元:元のファイル名、パス、サイズ、タイムスタンプ
- タイムライン再構築:ファイルの作成、変更、アクセス、削除イベント
- タイムスタンプ操作の検出:$SIと$FNのタイムスタンプの比較
- データカービングのガイダンス:MFTクラスタ実行がディスク上のファイル内容を指し示す
- アンチフォレンジック検出:ワイプや改ざんされたMFTレコードの識別
参考資料
- NTFS MFTアドバンストフォレンジック分析:https://www.deaddisk.com/posts/ntfs-mft-advanced-forensic-analysis-guide/
- MFTスラックスペースのフォレンジック価値:https://www.sygnia.co/blog/the-forensic-value-of-mft-slack-space/
- MFTECmdドキュメント:https://ericzimmerman.github.io/
- SANS FOR500:Windowsフォレンジック分析
出力例
$ MFTECmd.exe -f "C:\Evidence\$MFT" --csv /analysis/mft_output
MFTECmd v1.2.2 - MFTパーサー
==============================
入力:C:\Evidence\$MFT(サイズ:384 MB)
総MFTエントリ数:395,264
MFTエントリを解析中... 完了(12.4秒)
--- 削除ファイル復元サマリー ---
総エントリ数: 395,264
アクティブファイル: 245,832
削除ファイル: 149,432
復元可能: 87,234(常駐データ、またはクラスタが再割り当てされていない)
部分的に復元可能: 31,456(一部のクラスタが上書きされている)
復元不可: 30,742(すべてのクラスタが再割り当てされている)
--- 最近削除されたファイル(インシデント期間:2024-01-15から2024-01-18)---
MFTエントリ | ファイル名 | パス | サイズ | 削除日時(UTC) | 復元可能
----------|-------------------------------|------------------------------------|-----------|-----------------------|------------
148923 | exfil_tool.exe | C:\ProgramData\Updates\ | 1,258,496 | 2024-01-17 02:45:12 | はい
148924 | exfil_tool.log | C:\ProgramData\Updates\ | 45,312 | 2024-01-17 02:45:14 | はい
149001 | passwords.txt | C:\Users\jsmith\Desktop\ | 2,048 | 2024-01-17 02:50:33 | はい
149150 | scan_results.csv | C:\Users\jsmith\AppData\Local\Temp | 892,416 | 2024-01-17 03:00:01 | 部分的
149200 | mimikatz.exe | C:\Windows\Temp\ | 1,250,816 | 2024-01-18 01:15:22 | はい
149201 | sekurlsa.log | C:\Windows\Temp\ | 32,768 | 2024-01-18 01:15:25 | はい
149302 | .bash_history | C:\Users\jsmith\ | 4,096 | 2024-01-18 03:00:00 | いいえ
149400 | ClearEventLogs.ps1 | C:\Windows\Temp\ | 1,536 | 2024-01-18 03:01:12 | はい
--- $STANDARD_INFORMATION対$FILE_NAMEタイムスタンプ分析(タイムスタンプ操作検出)---
MFTエントリ | ファイル名 | $SI作成日時 | $FN作成日時 | 差分 | 判定
----------|---------------------|----------------------|----------------------|-----------|----------
148923 | exfil_tool.exe | 2023-06-15 10:00:00 | 2024-01-15 14:34:02 | -214日 | タイムスタンプ改ざん
149200 | mimikatz.exe | 2022-01-01 00:00:00 | 2024-01-16 02:30:15 | -745日 | タイムスタンプ改ざん
復元されたファイルの出力先:/analysis/mft_output/recovered/
完全なCSVレポート:/analysis/mft_output/mft_analysis.csv(395,264行)
タイムラインCSV:/analysis/mft_output/mft_timeline.csv