概要
- github.dev の VSCode Web版で 重大なセキュリティ脆弱性 を発見
- 攻撃者がリンクをクリックさせるだけ で GitHub トークンを窃取可能
- トークンは 全リポジトリ(プライベート含む)への読み書き権限 を持つ
- Webviewのサンドボックス不備 と キーボードイベントの誤処理 が原因
- 証拠コード(PoC)と 自己防衛策、VSCode側の対応も解説
GitHub.devとVSCode Webviewのセキュリティモデル
- github.dev は GitHubリポジトリを ブラウザ上でVSCode風に編集可能 なサービス
- OAuthトークン を github.com から github.dev へ渡して認証・操作を実現
- このトークンは 全リポジトリにアクセス可能 な広範な権限
- VSCode Web版は Webview(iframe)を用いてサンドボックス化
- Webview内のJavaScriptは 本体とは別オリジン で実行
- Node.js APIやVSCode APIへの直接アクセス不可
- Window.postMessage() で本体とWebview間の通信を実現
- 例:Markdownプレビューの行ハイライト同期など
脆弱性の詳細
- Webview内で キーボードイベント(keydown)が本体へ伝播 される仕様
- 本体はこれを ユーザー操作として扱う
- 攻撃者が 任意のキーボードイベントを偽造 し、危険なコマンドを実行可能
- 例:拡張機能のインストール、通知承諾など
- 拡張機能のインストール時にも 信頼性チェック回避の手口 が存在
- .vscode/extensions.json で 推奨拡張の通知 を表示
- Ctrl+Shift+A キーで通知の「インストール」を自動承認
- ローカル拡張機能 を用いて信頼性チェックをスキップ
- 拡張機能の package.json で任意のキーバインド追加 が可能
- 例:Ctrl+F1 で攻撃用コマンドを実行
攻撃の流れ(PoC)
- 攻撃用リポジトリに Jupyterノートブック と ローカル拡張機能 を配置
- ノートブックセル内の imgタグのonerror属性でJavaScriptを発動
- 攻撃スクリプトの流れ
- VSCodeの通知表示を待機
- Ctrl+Shift+A の偽造イベントで拡張インストールを承認
- 拡張インストール後、 Ctrl+F1 で追加コマンドを実行
- 攻撃拡張が GitHubトークンを窃取し、API経由でリポジトリ一覧取得
- 実際のPoC例:
防御策と推奨対応
- 信頼できないリポジトリやリンクをgithub.devで開かない
- Jupyterノートブックや拡張機能の内容確認 の徹底
- VSCodeのバージョンアップ・脆弱性情報の確認
- OAuthトークンの再発行・権限見直し
- ブラウザキャッシュや拡張機能の整理
VSCode側の対応と評価
- Webviewのキーボードイベント伝播仕様の見直し
- 拡張機能インストール時の信頼性チェック強化
- CSP(Content Security Policy)設定の改善
- 脆弱性報告に対する迅速な対応と開示
フルディスクロージャー(Full Disclosure)とタイムライン
- 脆弱性発見から報告、修正、公開までの流れ
- コミュニティやユーザーへの 透明性重視の情報公開
- セキュリティ研究者と開発元の協力体制 の重要性
まとめ
- github.devのVSCode Webviewは Webアプリ特有の脆弱性に注意
- リンククリック一発でGitHubトークン漏洩のリスク
- ユーザー自身の防衛意識 と VSCode側の継続的なセキュリティ改善 が不可欠