annotations について
idasql を通じて IDA データベースを編集するスキルです。逆コンパイル結果を注釈・整理するアナリスト向けに、コメントや名前、型、ブックマークの変更手順を提供します。
主な機能
- 01逆コンパイル・逆アセンブルのコメント編集
- 02ローカル変数の改名と型変更
- 03関数の要約とプロトタイプの更新
- 04フォルダーによる関数とブックマークの整理
- 05編集後の変更確認
活用シーン
- 01レビュー用の関数注釈
- 02逆コンパイル結果を読みやすくする改名
- 03調査対象のブックマークと分類
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ allthingsida/ idasql-skills --skill annotationsインストール後、Claude Code で/annotationsを入力して読み込まれたか確認します。
同梱ファイルagents/openai.yamlreferences/annotation-workflows.md
詳細
このスキルは、idasql を通じて IDA データベースを編集するためのガイドです。逆コンパイル結果、逆アセンブル、型情報に注釈を付けたり、名前を変更したり、型を再設定したり、コメントを追加したり、その他の変更を加えたりする必要がある場合に使用してください。
発動インテント
ユーザーが次の操作を求めた場合に、このスキルを使用します。
- コメントの追加・編集(疑似コード、逆アセンブル、関数の概要)
- シンボルやローカル変数の名前変更
- 型、列挙型、構造体の表現の適用
- 調査ワークフロー用のブックマークの作成・更新
- 疑似コードをソースコードのように読みやすくする
- 逆コンパイルしたコードをソースコードと並べてレビューできるように準備する
- コメントを1つ追加するだけでなく、関数全体に注釈を付ける
次のスキルに引き継ぎます。
- 編集前の分析には
decompiler - 宣言や構造体モデルの構築が必要な場合は
types - 再帰的なナラティブ/ソース復元パスには
re-source
最初に行うこと(ウォームスタート手順)
-- 1) Confirm target row/function before editing
SELECT * FROM funcs WHERE addr = 0x401000;
-- 2) Inspect current comment state
SELECT addr, line, comment
FROM pseudocode
WHERE func_addr = 0x401000
LIMIT 30;
-- 3) Inspect existing disassembly comments
SELECT * FROM comments WHERE addr BETWEEN 0x401000 AND 0x401100;
解釈のガイドライン:
- 確認せずに編集しないでください。変更前に、対象行が正確に一致していることを検証します。
- あいまいな名前の一致よりも、決定的なキー(
func_addr + addr、idx、slot)を優先します。
失敗と復旧
- 更新が「何もしていない」ように見える場合:
- 対象行を再読み込みし、逆コンパイルビューを更新して、配置フィールドを確認します。
- 誤った対象が変更された場合:
- 条件を絞り込み、再試行前に読み取りを先に行う手順を再実行します。
- 列挙型/構造体の表示が変わらない場合:
- 型/numform/ユニオン選択のサポートと対象コンテキストを確認します。
引き継ぎパターン
annotations-> 意味が不明確な場合はdecompiler。annotations-> 編集に不足している宣言が関係する場合はtypes。annotations-> 関数レベルのメモを再帰的なキャンペーンメモにする必要がある場合はre-source。
関数のコントラクトに注釈を付ける
annotate this function は、コメントを1つ追加する操作ではなく、関数全体を対象としたワークフローとして扱います。
デフォルトの動作:
- 現在の逆コンパイル結果とローカル変数/ラベルの状態を調べる
- 関数がソースコードのように読みやすくなる型/プロトタイプを適用する
- 可読性が大幅に向上する場合は、ローカル変数、グローバル変数、ラベルの名前を変更する
- 解釈に役立つ箇所に、対象を絞った行コメントを追加する
- ワークフローで永続的な分類先が作成される場合は、関数をレビュー/トリアージ用フォルダーに配置する
- 最後に必ず、
funcs.rpt_commentに再利用可能な関数コメントの概要をちょうど1つ追加する decompile(addr, 1)で更新し、結果を検証する
ユーザーが範囲を限定して依頼した場合のみ、より限定的なインテントを使用します。
add a comment-> コメントのみfunc-summary/function summary-> 概要のみannotate this function-> 全体の整理と概要
概要が必須である理由:
- 人間のレビュアーがすぐに全体像を把握できます
- 後でプログラム全体を理解するための、意味的に検索可能なプログラム知識を作成できます
フォルダーを活用した注釈ワークフロー
注釈を付けながら作業を整理するには、オブジェクトテーブルの folder_path 列を使用します。関数単位の作業には funcs.folder_path、グローバル変数/ラベルには names.folder_path、レビュー用の手掛かりには bookmarks.folder_path を優先します。dirtree_entries は生のブラウザーであり、dirtree_folders はすべての標準 IDA ディレクトリツリーの空フォルダーを管理します。
よく使うフォルダー:
idasql/review/needs-typesidasql/review/annotatedidasql/review/verifiedidasql/triage/networkidasql/triage/crypto
-- Create a review bucket and move selected functions into it
INSERT INTO dirtree_folders(tree, path)
VALUES ('funcs', 'idasql/review/needs-types');
UPDATE funcs
SET folder_path = 'idasql/review/needs-types'
WHERE addr = 0x401000;
-- Mark a function as annotated while adding the required repeatable summary
UPDATE funcs
SET folder_path = 'idasql/review/annotated',
rpt_comment = 'Parses command records, validates the opcode, and dispatches to command handlers.'
WHERE addr = 0x401000;
UPDATE names
SET folder_path = 'idasql/names/globals'
WHERE name LIKE 'g_%';
UPDATE bookmarks
SET folder_path = 'idasql/bookmarks/review'
WHERE description LIKE '%review%';
-- Review progress
SELECT folder_path, COUNT(*) AS functions
FROM funcs
WHERE folder_path LIKE 'idasql/%'
GROUP BY folder_path
ORDER BY folder_path;
オブジェクトをルートに戻すには、UPDATE ... SET folder_path = NULL WHERE ... を使用します。DELETE FROM dirtree_folders で削除されるのは、空のフォルダーのみです。フォルダーへの書き込みでは相対 / パスを使用します。./..、重複した区切り文字、バックスラッシュ、および既存の移動先への名前変更は拒否されます。
関数コメントの編集
実際の IDA 関数コメントは pseudocode やアドレス単位の comments テーブルではなく、funcs にあります。
用途:
- 通常の関数コメントには
funcs.commentを使用します - 反復可能な関数コメントには
funcs.rpt_commentを使用します
関数の要約に関するデフォルトの動作:
- 単数形の
add function commentは、UPDATE funcs SET rpt_comment = ...として扱います - ユーザーが非反復の関数コメントを明示的に求めた場合にのみ、
funcs.commentを使用します - 実際の関数コメントではなく、逆コンパイラーの注記/要約を明示的に求められた場合にのみ、見出し形式の
pseudocodeブロックコメントを使用します
標準的な SQL パターン:
SELECT addr, name, comment, rpt_comment
FROM funcs
WHERE addr = 0x401000;
UPDATE funcs
SET rpt_comment = 'One-paragraph summary of what the function does, inputs/outputs, and key behavior.'
WHERE addr = 0x401000;
逆コンパイラーコメントの編集(擬似コード)
pseudocode テーブルは、逆コンパイラーコメントを編集するための場所です。表示には decompile(addr) を使用し、編集にはテーブルを使用します。テーブルスキーマ全体については、decompiler スキルを参照してください。
重要な区別:
pseudocode.commentで編集されるのは Hex-Rays の逆コンパイラーコメントのみです。pseudocodeへの書き込みでset_func_cmt()が呼び出されることはありません。- 実際の関数コメントには
funcs.comment/funcs.rpt_commentを使用します。
書き込み可能な列:comment、comment_placement。配置:semi(; の後)、block1(独立した行の上)、block2、curly1、curly2、brace1、brace2、colon、case、else、do、asm、try。認識されない配置文字列は、通知なく semi に変換されます。
アンカーに関する指針:
- 推測した関数エントリー行ではなく、具体的な擬似コードのステートメント行を優先してください。
addrが複数の擬似コード行({、ステートメント、})に対応する場合は、まず一意の非ブレースアンカーを特定してください。line_numは候補行の確認にのみ使用してください。コメントの書き込みはaddr + comment_placementで永続化されます。同じaddrを共有する行には特に注意が必要です。表示された同じaddrの行がすべて個別に書き込み可能だと仮定しないでください。
書き込みの前にアンカーを確認してください:
SELECT line_num, addr, line, comment
FROM pseudocode
WHERE func_addr = 0x401000
ORDER BY line_num;
-- The example UPDATEs below assume 0x401020 is an already resolved writable
-- non-brace anchor from the inspection query above; do not substitute func_addr.
-- Edit: Add inline comment to decompiled code
UPDATE pseudocode SET comment_placement = 'semi',
comment = 'buffer overflow here'
WHERE func_addr = 0x401000 AND addr = 0x401020;
-- Edit: Add block comment (own line above statement)
UPDATE pseudocode SET comment_placement = 'block1', comment = 'vulnerable call'
WHERE func_addr = 0x401000 AND addr = 0x401020;
-- Edit: Delete comments at a resolved unique anchor
-- Warning: comment = NULL currently clears all placements at that addr.
UPDATE pseudocode SET comment = NULL
WHERE func_addr = 0x401000 AND addr = 0x401020;
-- Read edited pseudocode with comments
SELECT addr, line, comment FROM pseudocode WHERE func_addr = 0x401000;
孤立した逆コンパイラーコメントのクリーンアップ
データベースに、現在の擬似コードに紐付かない古い逆コンパイラーコメントが含まれている場合は、pseudocode 経由で消去しようとせず、孤立コメント用のサーフェスを使用してください。
読み取りを先に行うパターン:
SELECT func_addr, func_name, orphan_count
FROM pseudocode_v_orphan_comment_groups
ORDER BY orphan_count DESC
LIMIT 20;
SELECT addr, comment_placement, orphan_comment
FROM pseudocode_orphan_comments
WHERE func_addr = 0x401000
ORDER BY addr, comment_placement;
削除のみを行う変更パターン:
UPDATE pseudocode_orphan_comments
SET orphan_comment = NULL
WHERE func_addr = 0x401000
AND addr = 0x401020
AND comment_placement = 'semi';
注記:
pseudocode_orphan_commentsは削除専用です。- 空でない値の書き込みは拒否されます。
- トリアージにはグループ化されたサーフェスを使用し、その後、クリーンアップには正確なテーブルを使用してください。
- トリアージ後、迅速に処理するには両方のサーフェスで
WHERE func_addr = ...に切り替えてください。
関数の要約(func-summary)
function summary と func-summary は、同じ意図を表すものとして扱ってください。
トリガーの仕様:
- ユーザーが
function summaryまたはfunc-summaryと指定した場合、funcs.rpt_commentに反復可能な関数コメントをちょうど 1 つ追加または更新します。 - ユーザーが行を個別に指定せず、単数形の
add function commentと指定した場合は、反復可能な関数コメントの更新として扱います。 - ユーザーが逆コンパイラーの見出し注記または擬似コードのブロックコメントを明示的に求めた場合は、書き込み可能なアンカーを特定したうえで
pseudocode.commentを使用します。 - 多数の行コメントを追加するのは、ユーザーが行ごとの注釈/詳細な注釈を明示的に求めた場合に限ります。
デフォルトの動作:
- 要約は
funcs.rpt_commentに書き込みます。 - ユーザーが非反復の関数コメントを明示的に求めた場合にのみ、
funcs.commentを使用します。 - ユーザーが詳細な注釈を明示的に求めない限り、行ごとの注釈に展開しないでください。
- 関数に注釈を全面的に付ける場合は、意味的な最後のステップとして必ずこの要約を追加または更新してください。
長さに関する指針:
- 該当する場合は、最低 1 段落で記述してください。
- 単純なラッパー/サンク関数には、より短く簡潔な要約でもかまいません。
- 該当する場合は、関数の役割、主な入出力、重要な状態変更、注目すべき副作用を含めてください。
標準的な SQL パターン:
SELECT addr, name, comment, rpt_comment
FROM funcs
WHERE addr = 0x401000;
UPDATE funcs
SET rpt_comment = 'One-paragraph summary of what the function does, inputs/outputs, and key behavior.'
WHERE addr = 0x401000;
プロンプトの例:
function summary 0x401000func-summary DriverEntryfunc-summary this function
逆アセンブルのコメントを編集する
comments テーブルから逆アセンブルレベルのコメントを読み取ります。
SELECT COALESCE(NULLIF(comment, ''), NULLIF(rpt_comment, '')) AS comment
FROM comments
WHERE addr = 0x401000
LIMIT 1;
アップサートのセマンティクス: names テーブルと comments テーブルでは、すでに値が存在するアドレスに対する INSERT は既存のエントリを置き換えます(IDA では EA ごとに名前とコメントスロットはそれぞれ 1 つしか設定できません)。同じ場所での UPDATE も同等です。names では、IDA の SN_CHECK フラグによってグローバルな名前の競合も自動的に解消されます(例:別の EA ですでに使用されている場合、foo が foo_0 になることがあります)。書き込み後に行を読み戻し、実際に保存された値を確認してください。
comments テーブルでは、INSERT、UPDATE、DELETE がサポートされています。
| テーブル | INSERT | UPDATE 列 | DELETE |
|---|---|---|---|
comments | はい | comment、rpt_comment | はい |
INSERT INTO comments(addr, comment) VALUES (0x401000, 'regular comment');
INSERT INTO comments(addr, rpt_comment) VALUES (0x401000, 'repeatable comment');
UPDATE comments SET comment = 'updated comment' WHERE addr = 0x401000;
DELETE FROM comments WHERE addr = 0x401000;
注:
commentsの編集では、set_cmt()を使ってアドレスコメントを編集します。funcs.comment/funcs.rpt_commentの編集では、set_func_cmt()を使って実際の関数コメントを編集します。
ブックマーク
bookmarks テーブルでは、マークした位置とフォルダー構成を編集するための CRUD 操作をすべて実行できます。
| 列 | 型 | 説明 |
|---|---|---|
slot | INT | ブックマークのスロットインデックス |
addr | INT | ブックマークしたアドレス |
description | TEXT | ブックマークの説明 |
inode | INT | 読み取り専用の dirtree inode |
folder_path | TEXT | 書き込み可能なブックマークフォルダー。NULL はルートを意味します |
full_path | TEXT | 読み取り専用の dirtree フルパス |
-- List all bookmarks
SELECT printf('0x%X', addr) as addr, description, folder_path FROM bookmarks;
-- Edit: Add bookmark
INSERT INTO bookmarks (addr, description) VALUES (0x401000, 'interesting branch');
-- Edit: Update bookmark description
UPDATE bookmarks SET description = 'confirmed branch' WHERE slot = 0;
-- Edit: Move bookmark into a review folder
UPDATE bookmarks SET folder_path = 'idasql/bookmarks/confirmed' WHERE slot = 0;
-- Edit: Delete bookmark
DELETE FROM bookmarks WHERE slot = 0;
正規のスキーマと所有者の対応については、../connect/references/schema-catalog.md(bookmarks)を参照してください。
ローカル変数の編集(名前変更、型変更、コメント)
ctree_lvars テーブルは、デコンパイラーのローカル変数を編集するためのインターフェースです。書き込み可能な列は name、type、comment です。テーブルの完全なスキーマについては、decompiler スキルを参照してください。
ローカル変数の編集に関するガイダンス:
- 決定的に特定できる
idxを 1 つ調べて選択し、func_addr + idxで更新します。 - ローカル編集には
UPDATE ctree_lvars SET name = ...、type = ...、またはcomment = ...を使用します。 - 以前の名前ベースのワークフローでは、まず
func_addr + nameで候補行をクエリし、idxを 1 つ選択してから、そのidxで更新します。
-- Inspect current locals before renaming
SELECT idx, name, type, comment
FROM ctree_lvars
WHERE func_addr = 0x401000
ORDER BY idx;
-- Edit: Rename a local variable by index (canonical, deterministic)
UPDATE ctree_lvars SET name = 'buffer_size' WHERE func_addr = 0x401000 AND idx = 2;
-- Edit: Rename by current name after selecting one deterministic idx
UPDATE ctree_lvars SET name = 'buffer_size'
WHERE func_addr = 0x401000
AND idx = (
SELECT idx FROM ctree_lvars
WHERE func_addr = 0x401000 AND name = 'v2'
ORDER BY idx LIMIT 1
);
-- Edit: Set local-variable comment by index
UPDATE ctree_lvars SET comment = 'points to decrypted buffer' WHERE func_addr = 0x401000 AND idx = 2;
-- Edit: Change variable type
UPDATE ctree_lvars SET type = 'char *'
WHERE func_addr = 0x401000 AND idx = 2;
デコンパイラーのラベルを編集する
まず現在のラベルを読み取り、確認した正確なラベルの名前を変更してください。行テキストから推測するのではなく、label_num による識別を優先してください。
-- Inspect labels before renaming
SELECT label_num, name, printf('0x%X', item_addr) AS item_addr
FROM ctree_labels
WHERE func_addr = 0x401000
ORDER BY label_num;
-- Rename deterministically by label number
UPDATE ctree_labels SET name = 'fail' WHERE func_addr = 0x401000 AND label_num = 12;
-- Equivalent UPDATE path
UPDATE ctree_labels
SET name = 'fail'
WHERE func_addr = 0x401000 AND label_num = 12;
型の編集(作成、変更、適用)
型の作成、メンバーの CRUD、列挙値、parse_decls()、applied_types、および names / funcs を使った名前の書き込みについては、types スキルを参照してください。
注釈ワークフローで使用する、すぐに使える適用パターン:
-- Apply type to a function
UPDATE funcs SET prototype = 'void __fastcall exec_command(command_t *cmd);'
WHERE addr = 0x140001BD0;
-- Apply/replace the type at any mapped address
INSERT INTO applied_types(addr, decl)
VALUES (0x140001BD0, 'void __fastcall exec_command(command_t *cmd);');
オペランド表現の編集(逆アセンブルにおける列挙型/構造体)
instructions テーブルの operand*_format_spec 列を使って、オペランドの表示を編集できます。
-- Edit: Apply enum representation to operand 1
UPDATE instructions
SET operand1_format_spec = 'enum:MY_ENUM'
WHERE addr = 0x401020;
-- Edit: Apply struct-offset representation
UPDATE instructions
SET operand0_format_spec = 'stroff:MY_STRUCT,delta=0'
WHERE addr = 0x401030;
-- Edit: Nested member path uses '/' to separate type names
UPDATE instructions
SET operand0_format_spec = 'stroff:OUTER_T/INNER_T'
WHERE addr = 0x401030;
-- Edit: Clear representation back to plain
UPDATE instructions
SET operand1_format_spec = 'clear'
WHERE addr = 0x401020;
これらはすべて逆アセンブルレベルで使用でき、IDAPython は必要ありません。適用後に UPDATE が検証され、表現の変更が反映されなかった場合は SQL エラーが通知されます。
operand*_format_spec で指定できる値には、数値の基数やその他の表示形式も含まれます。
-- Number base / character
UPDATE instructions SET operand1_format_spec = 'hex' WHERE addr = 0x401020; -- also dec/oct/bin
UPDATE instructions SET operand1_format_spec = 'char' WHERE addr = 0x401020;
-- Offsets, sizeof, forced operand text
UPDATE instructions SET operand1_format_spec = 'offset:tbl_start' WHERE addr = 0x401020;
UPDATE instructions SET operand1_format_spec = 'sizeof:MY_STRUCT' WHERE addr = 0x401020;
UPDATE instructions SET operand1_format_spec = 'forced:5 shl 3' WHERE addr = 0x401020;
-- Sign / bitwise-not modifiers (combine with a base, or use alone)
UPDATE instructions SET operand1_format_spec = 'dec,signed' WHERE addr = 0x401020;
その他の種類:float、segment、stkvar、および ,unsigned / ,bnot / ,nobnot 修飾子。完全な一覧については、disassembly スキルを参照してください。
デコンパイル済みコードのユニオン選択を編集する
ユニオン選択ヘルパー(set_union_selection*、get_union_selection*)については、decompiler スキルを参照してください。
数値形式の編集(デコンパイル済みコードにおける列挙型の表示)
推奨: 変数の型を列挙型に変更してください。IDA のデコンパイラーは、すべての定数を列挙型名で自動的に表示するようになります。
-- 1. Define the enum type (skip if it already exists)
SELECT parse_decls('typedef enum { DLL_PROCESS_DETACH=0, DLL_PROCESS_ATTACH=1 } fdw_reason_t;');
-- 2. Retype the parameter/variable
UPDATE ctree_lvars SET type = 'fdw_reason_t'
WHERE func_addr = 0x180001050 AND idx = 1;
-- 3. Verify
SELECT decompile(0x180001050, 1);
オペランドごとの数値形式の制御(set_numform*、get_numform*)については、decompiler スキルを参照してください。
必須の変更ループ(すべての編集に適用)
connectのグローバルエージェント契約で定義されている「読み取り -> 編集 -> 更新 -> 検証」のサイクルに従ってください。
一括編集のパフォーマンスに関するヒント
多くの関数や注釈を編集するときは、次のコストを考慮してください。
decompile(addr, 1)は完全な再デコンパイルを実行します(関数ごとに約50~200ms)。同じ関数内の複数の項目を編集する場合は、更新前にすべての編集をまとめてください。-- Good: structural typing first, then refresh, then naming cleanup UPDATE ctree_lvars SET type = 'MY_CTX *' WHERE func_addr = 0x401000 AND idx = 0; SELECT decompile(0x401000, 1); UPDATE ctree_lvars SET name = 'ctx' WHERE func_addr = 0x401000 AND idx = 0; UPDATE ctree_lvars SET name = 'size' WHERE func_addr = 0x401000 AND idx = 1; SELECT decompile(0x401000, 1); -- final refresh after cleanuppseudocodeのコメント書き込みでは対象の関数が再デコンパイルされます。書き込みのたびに、コメントのアンカーを解決するために対象の関数をデコンパイルし、コメントを IDA のユーザーコメントストアに保存したうえで、その関数のデコンパイラーキャッシュを無効化します。そのため、次回のdecompile(addr)で再レンダリングされます。コメントを書き込むたびに自分でdecompile(addr, 1)を呼び出す必要はありませんが、書き込みにはコストがかかり、その関数のデコンパイルが1回分発生します。ctree_lvarsの型変更ではデコンパイラーキャッシュが無効になります。変数の型を変更した後は、idxや名前に基づくクリーンアップを行う前に更新してください。デコンパイラーによってローカル変数が分割されたり、式が再レンダリングされたりする場合があります。- 大規模なデータベースでは
save_database()に時間がかかる場合があります。注釈作業では、編集のたびに保存するのではなく、すべての書き込みをまとめて最後に一度だけ保存してください。
追加リソース
- クリーンアップワークフローの全体、一括注釈のパターン、完全な実例については、references/annotation-workflows.md を参照してください。
関連項目
types— 型辞書の項目を定義および変更し、applied_typesまたはfuncs.prototypeを通じて適用します。decompiler— 疑似コードのコメント(UPDATE pseudocode SET comment = ...)、ctree のローカル変数の名前変更と型変更。disassembly— コードラベルの名前変更(names)、命令レベルのオペランド形式の適用。