rev-u3d-dump について
rev-u3d-dumpは、Unity IL2CPPビルドからC#のメソッド名、アドレス、型定義を抽出し、IDAやGhidraでの解析に使うスキルです。ネイティブバイナリとメタデータの対応付け、ツール選択、結果の取り込み手順を扱います。
主な機能
- 01メソッド名とアドレスの抽出
- 02C#型定義のダンプ
- 03メタデータバージョンの確認
- 04IDA/Ghidra用インポートファイルの生成
- 05IL2CPPビルドファイルの特定
活用シーン
- 01IDAで関数名を復元
- 02型定義をバイナリ解析に取り込む
- 03Unity IL2CPPビルドを解析
インストール
コマンドをコピーしてターミナルで実行します。
$
npx skills add https:/ / github.com/ p4nda0s/ reverse-skills --skill rev-u3d-dumpインストール後、Claude Code で/rev-u3d-dumpを入力して読み込まれたか確認します。
詳細
rev-u3d-dump - Unity IL2CPP シンボルダンパー
IDA/Ghidra での解析に向けて、Unity IL2CPP ビルドから C# のメソッド名、アドレス、型定義を抽出します。
概要
Unity IL2CPP は C# をネイティブコードにコンパイルします。元のクラス名やメソッド名はバイナリから削除されますが、global-metadata.dat には保持されています。このツールは、ネイティブ関数のアドレスと元の C# 名との対応関係を復元します。
Unity ビルドの主要ファイル
| ファイル | 場所 | 用途 |
|---|---|---|
| ネイティブバイナリ | iOS: Frameworks/UnityFramework.framework/UnityFrameworkAndroid: lib/{arch}/libil2cpp.so | コンパイル済み C# コード(Mach-O/ELF) |
| メタデータ | Data/Managed/Metadata/global-metadata.dat | すべての型/メソッド/文字列情報 |
ツールの選択
Il2CppDumper(メタデータ v39 以降に推奨)
Unity 6 以降のビルドでは、v39 フォークを使用します。
- リポジトリ:
https://github.com/roytu/Il2CppDumper(ブランチ:v39) - メタデータ v24~v39 に対応
- 関数アドレスを含む
script.jsonを出力し、IDA/Ghidra にそのままインポートできます
オリジナルの Il2CppDumper(https://github.com/Perfare/Il2CppDumper)は、v29 までしか対応していません。
Cpp2IL(代替)
- リポジトリ:
https://github.com/SamboyCoding/Cpp2IL - メタデータ v39 に対応していますが、ダミー DLL に
[Address]属性がありません - C# ソースの再構築には役立ちますが、IDA へのインポートには適していません
手順
手順 1:IL2CPP ファイルを見つける
iOS(IPA):
# Unzip IPA
unzip -o app.ipa -d .
# Binary
BINARY="Payload/<AppName>.app/Frameworks/UnityFramework.framework/UnityFramework"
# Metadata
METADATA="Payload/<AppName>.app/Data/Managed/Metadata/global-metadata.dat"
Android(APK):
# Unzip APK
unzip -o app.apk -d .
# Binary (pick target arch)
BINARY="lib/arm64-v8a/libil2cpp.so"
# Metadata
METADATA="assets/bin/Data/Managed/Metadata/global-metadata.dat"
手順 2:メタデータのバージョンを確認する
# First 8 bytes: magic (4) + version (4), little-endian
xxd -l 8 "$METADATA"
# Expected: af1b b1fa 2700 0000 → magic OK, version = 0x27 = 39
| バージョン | Unity | ツール |
|---|---|---|
| ≤ 29 | Unity 2021 以前 | オリジナルの Il2CppDumper |
| 31 | Unity 2022 | オリジナルの Il2CppDumper(一部対応) |
| 39 | Unity 6(6000.x) | roytu/Il2CppDumper v39 フォーク |
手順 3:Il2CppDumper(v39 フォーク)をビルドして実行する
# Clone v39 fork
git clone -b v39 https://github.com/roytu/Il2CppDumper.git
# Build
cd Il2CppDumper
DOTNET_ROLL_FORWARD=LatestMajor dotnet build -c Release
# Run (use net8.0 framework)
DOTNET_ROLL_FORWARD=LatestMajor dotnet run \
--project Il2CppDumper/Il2CppDumper.csproj \
-c Release --framework net8.0 \
-- "$BINARY" "$METADATA" output_dir
注意:
DOTNET_ROLL_FORWARD=LatestMajorを設定すると、プロジェクトが .NET 6/8 を対象としていても、.NET 9/10 で実行できます- 非対話モードでの終了コード 134 は正常です(最後の
Console.ReadKey()が原因です) - macOS でバイナリが SIGKILL で終了される場合は、アドホック署名を付与します:
codesign -s - <binary>
手順 4:出力を確認する
正常に実行されると、出力ディレクトリに次のファイルが生成されます。
| ファイル | サイズ(一般的な値) | 用途 |
|---|---|---|
script.json | 50~100 MB | 関数アドレス+名前+シグネチャ(IDA/Ghidra へのインポート用) |
dump.cs | 10~30 MB | RVA/VA アドレスを含む C# クラスダンプ |
il2cpp.h | 50~100 MB | 型のインポート用 C 構造体定義 |
ida_py3.py | 約 2 KB | IDA Python インポートスクリプト |
script.json の形式を確認します。
{
"ScriptMethod": [
{
"Address": 40865744,
"Name": "ClassName$$MethodName",
"Signature": "ReturnType ClassName__MethodName (args...);",
"TypeSignature": "viii"
}
]
}
dump.cs の形式を確認します。
// RVA: 0x1A2B3C4 Offset: 0x1A2B3C4 VA: 0x1A2B3C4
public void MethodName() { }
手順 5:IDA にインポートする
- IDA でネイティブバイナリ(UnityFramework/libil2cpp.so)を開きます
script.jsonとida_py3.pyを同じディレクトリに配置しますFile → Script file...→ida_py3.pyを選択します- スクリプトが
script.jsonを読み込み、すべての関数の名前を自動変更します - 任意:
File → Load file → Parse C header file...→il2cpp.hを選択して構造体型を読み込みます
手順 5(代替):Ghidra にインポートする
- Ghidra でバイナリを開きます
- Il2CppDumper に含まれる
ghidra.pyまたはghidra_with_struct.pyスクリプトを使用します - 同じディレクトリに
script.jsonを配置し、Window → Script Manager → Runを実行します
トラブルシューティング
| エラー | 原因 | 対処方法 |
|---|---|---|
not a supported version[39] | オリジナルの Il2CppDumper を使用している | roytu/Il2CppDumper v39 フォークに切り替えます |
| 終了コード 137(SIGKILL) | macOS でバイナリが未署名 | codesign -s - <binary> |
Cannot read keys(終了コード 134) | 非対話型コンソール | 無視してください。ダンプは正常に完了しています |
DOTNET_ROLL_FORWARD エラー | .NET のバージョン不一致 | DOTNET_ROLL_FORWARD=LatestMajor を設定します |
| 出力が空 | バイナリとメタデータの組み合わせが誤っている | 両方のファイルが同じビルドのものか確認します |
出力の活用に関するヒント
dump.csは最も手早く参照できます。RVA アドレスを使ってクラス名やメソッド名を検索してくださいscript.jsonの Address 値は 10 進数です。IDA で使用するには 16 進数に変換します:hex(40865744)→0x26F8FD0dump.csのフィールドオフセット(例:// 0x20)はオブジェクトのベースからの相対値であり、Frida を使ったメモリ検査に役立ちます
コメント
Markdown 対応