概要
- Scratch はSVG関連の脆弱性を長年抱えている
- SVGの サニタイズ 対策は毎年新たな問題が発覚し続けている
- XSSや HTTPリーク など多様な攻撃手法が発見されてきた
- 複雑化する サニタイズ処理 でも完全な安全性は実現できていない
- 今後も 新たな脆弱性 が発生し続ける可能性が高い
ScratchにおけるSVGサニタイズの歴史と課題
- Scratch はユーザー生成SVGをDOMに挿入し、信頼性の高いバウンディングボックス計測などの目的で利用
- SVGのDOM挿入はどんなに短時間でも 根本的に危険な操作
- サニタイズのために複雑なパーサやフィルタを増築するアプローチを採用
- しかし 根本的な解決には至らず、毎年新しい抜け道が発見される状況
2019年:scriptタグによるXSS
- SVG内の <script>タグ でJavaScriptが実行され、XSSが発生
- 攻撃者は他ユーザーの権限でコメント投稿・プロジェクト削除等が可能
- Scratch Desktopでは Node.js統合 により任意コード実行にも発展
- 正規表現でscriptタグ除去することで一時的に対策
2020年:正規表現の不備によるXSS(CVE-2020-7750)
- 大文字<SCRIPT> やイベントハンドラ属性(onerror等)で回避可能
- DOMPurify導入でscript除去を強化
2022年:image要素のhrefによるHTTPリーク
- <image>要素の href属性 で外部リクエスト発生
- DOMPurifyは実行コードは除去するがHTTPリークは防げず
- IPアドレス漏洩 や位置情報推測が可能
- DOMPurifyのフックで外部URLのhrefを除去することで対策
2023年:CSS @importによるHTTPリーク
- <style>内の **@import** で外部リクエスト誘発
- JavaScript製CSSパーサを導入し、@importを除去
2024年:Paper.js経由のXSS
- サニタイズ前のSVGが Paper.js (コスチュームエディタ用ライブラリ)に渡されXSS
- scratch-svg-rendererだけでなくPaper.js読み込み時にもサニタイズ適用
- サーバー側でも何らかの保護があるとされるが詳細不明
2025年:CSS url()によるHTTPリーク
- CSSの url() 関数で外部リクエスト発生
- style属性や<style>内のurl()を検出し除去する処理を追加
2026年:サニタイズコードのバグによるHTTPリーク
- エスケープコード によるurl()の回避
- style属性内で複数のurl()がある場合の不備
- CSS変数(var(--name))経由のurl()参照
- さらなる複雑なサニタイズ処理追加で対応
2026年:長大なCSSトランジションによる全ページ再スタイリング
- SVG内の 長いtransition と全要素へのtransform適用で、ページ全体のスタイルを攻撃者が操作可能
- reportボタン非表示、likeボタン巨大化、偽の案内表示など フィッシング 等の悪用例
- 現在も未修正
2026年:image-set()によるHTTPリーク
- CSSの image-set() 関数で外部リクエスト発生
- url()以外の方法でHTTPリークが可能
- 現時点で未修正
20XX年:新しいCSS仕様による将来的なHTTPリーク
- CSS Units Level 4やCSS Images Level 4など 新仕様 の実装進展で、また新たな攻撃手法が登場する可能性
サニタイズの限界と今後の展望
- SVGサニタイズの複雑化 は進むが、イタチごっこの様相
- SVG仕様・CSS仕様の拡張やブラウザ実装の変化により 新たな抜け道 が定期的に発生
- 根本的な安全性確保は困難 であり、SVGのDOM挿入自体を極力避ける設計が望ましい
- Scratchに限らず、 ユーザー生成SVG を扱う全てのサービスで同様のリスクが存在