SHA ピン留めは検証ではない:Plugin4Shell と初の AI エージェントサプライチェーン RCE
925 個のプラグインスキルが既に原本のメンテナーからハイジャックされており、それらのスキルは 134,000 エージェントに届いています。2026 年 9 月 17 日、AIR Security は Plugin4Shell を公開しました — AI エージェントエコシステム初のサプライチェーン脆弱性です。Claude Code、OpenAI Codex、GitHub Copilot、Google Gemini CLI に影響するゼロクリックのリモートコード実行(RCE)で、すべて同じ欠落したチェックを通じて発生します。メカニズムは、影響を受けたすべてのエージェントがスキップする 1 つの git アサーションです。エージェントは marketplace がピン留めした commit SHA をチェックアウトしますが、ワーキングツリーがその commit に実際に到達したことを検証しません。プラグインのリポジトリを支配する攻撃者は、ピン留めされた 40 文字の SHA と同じ名前のブランチを作成してリポジトリのデフォルトに設定し、エージェントはピン留めされた commit でのクリーンなインストールを報告しながら攻撃者制御のコードをインストールします(Cyber Security News、Help Net Security)。
これは、本番システムに対してコーディングエージェントを実行するあらゆるチームにとって重要です。なぜなら、ピンこそが制御だったからです。コミュニティの marketplace を超える組織 — プラグインコードをレビューし、レビュー済みの commit にインストールをピン留めする組織 — は SHA ピン留めを安全装置として信頼していましたが、Plugin4Shell はそれを静かに無効化します。レビューは通り、ピンは書き込まれ、別のコードが実行されるのです(AIR)。本記事では、次のプラグイン自動更新が発火する前にエンジニアリング責任者が知るべき 4 つのことを取り上げます。1 つの git コマンドで語れるメカニズム、良性の採用からバックグラウンド RCE までの 5 ステップの攻撃、ベンダーの対応スコアボード(2 社修正済み、1 社未修正、1 社非推奨かつ未修正)、そしてエージェントがインストールするピン留めされたあらゆる成果物 — プラグイン、MCP サーバー、スキル — のギャップを塞ぐ検証項目です。
重要なポイント
- ゼロクリック RCE が 4 大コーディングエージェントすべて — Claude Code、Codex、GitHub Copilot、Gemini CLI — を 1 つの欠落した git アサーションを通じて襲った — AIR は 2026 年 9 月 17 日に Plugin4Shell を公開しました。エージェントは marketplace がピン留めした commit SHA をチェックアウトしますが、チェックアウトがその commit に解決されたことを検証しないのです(AIR)。
- 925 個のスキルが既にメンテナーからハイジャックされ、134,000 エージェントに届いている — AIR の SkillJacking 研究。Plugin4Shell は、まさにこの種のリポジトリ乗っ取りを封じ込めるために構築された SHA ピン留め機構を突破します(AIR)。
- Git はハッシュそのものよりハッシュと同じ名前のブランチを優先する — ピン留めされた 40 文字の SHA を名前に持つブランチがリポジトリのデフォルトに設定されると、
git checkout <sha>は攻撃者コードへリダイレクトされます。Gemini CLI の変種は代わりにFETCH_HEADを攻撃面にします(Cyber Security News)。 - ベンダースコアボードは 2 社修正済み、1 社未修正、1 社非推奨かつ未修正 — Anthropic は Claude Code を 2.1.179 で、OpenAI は Codex を 0.146.0 で修正しました。Microsoft は Copilot の修正を公開しておらず、Google は Gemini CLI を未修正のまま非推奨化したため、既存のインストールはすべて暴露され続けます(Help Net Security)。
- 両バリアントを塞ぐのは 1 つのアサーション:チェックアウト後に解決された HEAD をピン留め SHA と照合する —
test "$(git rev-parse HEAD)" = "<pinned-sha>" || abort— そしてそれはエージェント内部で実行されなければなりません。解決しないピンを marketplace が強制できるわけがないからです(AIR)。
下の図は、この開示を 1 分に圧縮したものです。5 ステップの攻撃チェーン、3 日時点のベンダースコアボード、そしてギャップを塞ぐアサーション。
メカニズム:1 つのアサーション、4 つのエージェント
SHA ピン留めは、marketplace のセキュリティモデルが設計どおりに機能している状態です。レビュアーが特定の commit でプラグインを検査し、marketplace がその commit の SHA を記録し、エージェントは永遠にそのコードをインストールするはずでした。失敗は最後のステップにあります。影響を受けたすべてのエージェントが実行するのは、おおよそ次のシーケンスです(AIR):
git clone ./
git checkout aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa # ピン留めされた SHA そして、チェックアウトがピン留めされた commit に実際に着地したかを尋ねません。この欠落が悪用可能なのは、git がオブジェクトより先に名前を解決するためです。ある名前が有効な ref と commit ハッシュの両方であれば、git は ref を優先し、refname is ambiguous 警告を出すだけです。すでに上流リポジトリを支配する攻撃者は、正確な 40 文字の 16 進数ピン SHA と同じ名前のブランチを作成し、それをリポジトリのデフォルトに設定します。通常の git clone はそのブランチをローカル ref として取り込み、git checkout <sha> はブランチに解決され、ワーキングツリーは攻撃者制御となり、エージェントはピン留め SHA でのインストール成功を報告します(Cyber Security News)。
このトリックが成立する条件は 2 つ。第一に、ハッシュと同じ名前のブランチを普遍的に阻止するものは何もない。git 自身の check-ref-format は 40 文字の 16 進名を受け入れ、GitHub は完全に拒否しますが、Bitbucket と自ホストの git サーバーは許可します — そして Anthropic 自身のドキュメントは Bitbucket と自ホスト git を有効な marketplace バックエンドとして挙げています(AIR)。第二に、ブランチはリポジトリのデフォルトでなければなりません。非デフォルトのブランチはリモート追跡 ref としてしか到達せず、チェックアウトは本物の commit にフォールバックします。
Gemini CLI は別のやり方で失敗します。そのインストールシーケンスは、ピン留めされた commit を fetch した後で FETCH_HEAD をチェックアウトします:
git clone --depth 1 ./
git fetch origin 41d0bc0a4aeb2fbf797dacea39e876d98c95024b
git checkout FETCH_HEAD リポジトリのデフォルトブランチ自体が FETCH_HEAD という名前なら、チェックアウトはそのブランチに解決され、fetch した commit を静かに捨てます(AIR)。コマンドは違っても、根本原因は同じです。エージェントは要求した名前を信頼し、受け取った commit を検証しない。
5 ステップの攻撃:採用から RCE まで
どちらの攻撃経路も marketplace の支配を必要としません。AIR は両方を実演しました:
- 仕込み。 攻撃者は真正に良性のプラグインを、commit
aaa…aaaにピン留めして公開します。レビューを通過します。 - 採用。 ユーザーがインストールします。すべてのインストールはレビュー済み commit にピン留めされます。
- 再ピン留め。 攻撃者はまだ良性の例常的な更新を公開し、marketplace が pin を
bbb…bbbに引き上げます。 - すり替え。 攻撃者は
bbb…bbbと名付けたブランチを作成し、リポジトリのデフォルトに設定し、悪意あるコードを指します。ピン留めされた commit 自体は無傷のままで構いません。 - 自動更新から RCE へ。 変更された pin がすべてのエージェントのバックグラウンド自動更新をトリガーします — Claude Code と Codex のデフォルト動作 — チェックアウトは新しい pin をブランチに解決し、クリックなし、プロンプトなし、再インストールなしでコードが実行されます(AIR)。
代替経路はより高速です。正当なメンテナーのリポジトリを乗っ取り、仕込みステップを丸ごと省略するのです。AIR の姉妹研究は、これがどれほど一般的かを定量化しています — 925 個のスキルが原本のメンテナーからハイジャックされ、134,000 エージェントに届いています(AIR)。これは三部作の第三幕です。The Story of Skills は悪意あるスキルが 26,000 エージェントに届く様子を示し、MCPJacking は期限切れドメインを通じて公式 marketplace の 155 個のハイジャック可能な MCP サーバーを発見しました。研究者たちはそれらのドメインを登録し、信頼するすべてのエージェントでリモート prompt 実行を得ました(AIR)。Plugin4Shell は、業界がこのすべてを封じ込めるために構築した機構の境界破綻です。爆発半径はエージェントよりも広いのです。プラグインとアドオンは、エージェントを実行する開発者の権限を継承します — ローカルのソースコード、クラウド認証情報、SSH キー、内部リポジトリ、そして本番システムです(Cyber Security News)。
ベンダースコアボード:2 社修正済み、1 社未修正、1 社非推奨未修正
開示のタイムラインは、調整済み開示が機能したこと — と、それがどこで止まったか — を示しています:
| いつ | 何が |
|---|---|
| 2026 年 5 月 | AIR が欠陥を発見。4 つのエージェントすべてに対する動作する PoC |
| 2026 年 6 月 | 4 ベンダーへの調整済み開示 |
| 2026-06-17 | Anthropic が Claude Code 2.1.179 での修正を確認 |
| 2026-08-04 | Google が修正しないことを確認 — Gemini CLI は非推奨。ユーザーは Antigravity への移行を案内される |
| 2026-08-12 | OpenAI の Codex 0.146.0 が修正済みと確認 |
| 2026-09-17 | 公開開示 |
9 月 18〜19 日時点で、スコアボードは変わっていません。Anthropic 修正済み、OpenAI 修正済み、Microsoft は Copilot の修正を未公開、Google は Gemini CLI を未修正のまま非推奨化 — つまり、既存の Gemini CLI インストールはすべて無期限に暴露され続けます(Help Net Security)。GitHub の対応 — プラットフォーム上で SHA 形状のブランチ名とタグ名を禁止 — はギャップを閉じません。marketplace は Bitbucket や自ホスト git サーバー上にホストでき、そこではそのような名前が今も合法だからです(Cyber Security News)。
AIR の要約が最も正直です。"The fix has to ship in the agent, and updating is the only complete mitigation where one exists"(AIR)。構造的な理由は、調達の会話のためにあえて再述する価値があります。pin はエージェント内部で解決されるため、marketplace は自らが宣伝する保証を強制できないのです。ベンダー側の marketplace アップロードスキャン(Anthropic は 2026 年 8 月 6 日に Skill/Plugin Scanning を提供)は、悪意あるプラグインが marketplace に入る確率を下げますが、エージェント側のチェックアウト検証の代わりにはなりません。すり替えはレビューの後、解決の時点で起こるからです(MCP Security Hardening Checklist)。これはまた、ガバナンスの実例でもあります。4 つのベンダー、1 つの共通設計欠陥、そして 3 日間続く非対称な対応 — 調達組織はこれを、ベンダーのセキュリティパッチ適用 cadence を縮図として読むことができます。
チェックアウト後の検証:一般化される制御
AIR の 1 行の修正が両バリアントを塞ぎます(AIR):
test "$(git rev-parse HEAD)" = "" || abort 詳細が教訓を運びます。git rev-parse HEAD は、ワーキングツリーが実際に含むものを解決します — 要求された名前ではありません。この区別こそ、Gemini の FETCH_HEAD 変種がすり抜けた箇所です。そしてチェックはエージェント内部で実行されなければなりません。pin はクライアントで解決されるからです。チェックアウト後に検証する marketplace は、自分の記録を検証しているだけです。不一致のときに中止しなければならないコンポーネントはエージェントです。
このパターン — 解決の後ではなく前にではなく、後で検証する — は、エージェントスタックのピン留めされたあらゆる成果物の制御に一般化できます。ピン留めされた MCP サーバーのバージョン、ピン留めされたスキル、ピン留めされたモデルの重み、ピン留めされたコンテナ digest:どれも、あるインストーラが守ると信頼され、誰もその解決を検証しない主張です。同じ欠落したアサーションは、チェックアウトが起きるすべての場所に存在します。今週取り組むべき 4 つの項目:
- 修正があるエージェントを更新する。 Claude Code を 2.1.179 以降へ、Codex を 0.146.0 以降へ。Copilot と Gemini CLI には修正がありません — 修正が公開されるまで、これらのエージェントの到達範囲(ファイルシステム、認証情報、ネットワーク出口)を制限するか、ベンダーの移行パスに従います。
- ピン留めされたすべての成果物を棚卸しする。 プラグイン、スキル、MCP サーバーのバージョン、内部インストーラ。それぞれについて、解決済み HEAD のアサーションをスキップするコードパスがないか確認します — これはベンダーのエージェントだけでなく、チームが書いた内部ツールも含みます。
- プラグインリポジトリの乗っ取りシグナルを監査する。 予期しないブランチ変更、デフォルトブランチの移動、所有権の移転。ハイジャックされた 925 個のスキルは、この開示の前に奪われていました。リポジトリ乗っ取りは入口のステップで、すでに大規模に運用されています(Cyber Security News)。
- プラグインの自動更新を、便利機能ではなくサプライチェーンの配送チャネルとして扱う。 エージェントが pull できる marketplace とリポジトリを許可リストに載せ、エージェントの設定が許す限り、再ピン留めを再レビューの下に置きます。ゼロクリックの性質は自動更新から来ます — 「ゼロ」を取り除けば、攻撃には再びユーザーのアクションが必要になります。
2 つの隣接 CVE と、続く暴露
同じ週に、Plugin4Shell と同じテーマを持つ 2 つの MCP サーバー CVE が出ました — 呼び出し元を決して検証しないコンポーネントに置かれた信頼です。CVE-2026-54618 は 0.2.0 未満の Obsidian Web MCP に影響します。OAuth 認可エンドポイントがユーザーを認証せずに任意の呼び出し元へコードを発行し、未認証のリモート攻撃者に vault 全体への読み取り、書き込み、検索、移動、削除の完全なアクセスを与えていたもので、0.2.0 で修正されました(Rapid7、GitHub advisory GHSA-hwhg-mrjc-8g43)。CVE-2026-54446 は NetLicensing-MCP の認証欠落の欠陥(CWE-306)です(Practical DevSecOps)。これらは、数か月間動いていない生態系の基線数値の上に積み重なります。MCP の月間ダウンロード数は 97M+、サンプリングされたサーバーの 82% がパス走査に脆弱、OAuth を使うのはわずか 8.5% です(Practical DevSecOps)。
3 つの開示を貫くパターンは、エージェントスタックのすべての層で同じです。ある信頼の機構 — ピン、OAuth フロー、サーバー エンドポイント — が、間違った時にチェックを実行するか、まったく実行しない。Plugin4Shell は、単一の製品からエコシステム全体へ一気に越境した最初の事例にすぎません。
関連記事
- MCP Security Hardening Checklist: 1,467 Exposed Servers and the Controls That Close Them — この脆弱性が収まる 12 制御のベースライン:Plugin4Shell はサプライチェーン層(制御 5–7)に属し、Skill/Plugin Scanning の更新の隣です
- Shadow AI Agents: 17,800 Add-Ons, 6.7 Million Installations, and the Runtime Control Gap — ハイジャックされたアドオンに気づくかどうかを決める、インベントリと実行時制御のギャップ
- The First MCP CVE on the KEV List Hit Its Federal Deadline: LiteLLM and the Default-Key Vault — 連邦修復期限に達した MCP CVE、そしてそれを塞ぐ 6 つのゲートウェイ検証項目
ある中堅の工業系販売代理店は、内部ツール用に Claude Code を実行し、NetSuite と 2 つのサプライヤ カタログに対して見積もる調達エージェントを運用しています。チームは両方の面でピン留めされたすべての成果物を棚卸しし、Claude Code を 2.1.179 に更新し、プラグインのバックグラウンド自動更新を無効化し、内部の MCP モジュール インストーラに解決済み HEAD のアサーションを追加しました。プラグインのソースはレビュー済み 2 リポジトリの許可リストへ移され、監査証跡はすべての再ピン留めをその差分とともに記録します。次の marketplace インシデントは、インシデント対応ではなく、バージョン更新とレビューになります。
スコープを絞ったビルドをご相談ください。 1 週間のディスカバリー。システム棚卸し、ワークフロー マップ、固定スコープをお渡しします — 私たちと一緒にビルドするかどうかにかかわらず。
あなたのシステムのためにこれを構築したいですか?
ここの各ドキュメントは実際の本番作業から来ています。ターゲットシステムとワークフローがあれば、1週間でスコープを定義できます。
スコープ付き構築を依頼1週間のディスカバリ。システムインベントリ、ワークフローマップ、固定スコープを提供します — 私たちと構築するかどうかにかかわらず。