
目に見えない Unicode 双方向文字は、ソースコードを実行時とは異なる表示にすることができます。これが CVE-2021-42574 — Trojan Source 攻撃です。
攻撃者はテキストの方向を反転させる文字を埋め込みます。コードレビューでは、こう見えます:
access_level = "admin"
しかしコンパイラにはこう見えます:
access_level = "user"
これらの文字は目に見えません。エディタにも表示されず、レビュアーも気づきません。bidi-guard なら見つけられます。
pip install bidi-guard
# Scan current directory recursively
bidi-guard scan .
# Scan a specific file
bidi-guard scan src/auth.py
すべての双方向 Unicode 文字を検出し、正確な位置、コンテキスト、深刻度を表示します。
name: BiDi Guard
on: [push, pull_request]
jobs:
bidi-scan:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions/setup-python@v5
with:
python-version: "3.11"
- run: pip install bidi-guard
- run: bidi-guard ci .
.pre-commit-config.yaml に追加:
repos:
- repo: https://github.com/Moshe-ship/bidi-guard
rev: v0.1.0
hooks:
- id: bidi-guard
Unicode の双方向制御文字 全16種類:
高または重大とマークされた文字は、表示されるテキストを能動的に並べ替えることができます — Trojan Source 攻撃で使われるのはこれらの文字です。
from bidi_guard import scan_file, Finding
findings = scan_file("src/auth.py")
for f in findings:
print(f"{f.char_name} at line {f.line}:{f.col} — severity: {f.severity}")
これらの文字は目に見えません。文字通り、目に見えないのです:
grep "RLO" file.py # finds nothing
cat file.py # looks completely normal
bidi-guard は grep には見えないものを表示します: 正確な文字、その位置、周囲のコンテキスト、深刻度、そしてその働きです。さらに、それらを除去して自動修正することもできます。
MIT — Musa the Carpenter
このツールは Saudi AI Community によって提供されています — まずアラブ人へ、そして広く世界へ。
| コマンド | 説明 |
|---|
scan | 双方向文字をファイルからスキャンし、コンテキスト付きで結果を表示 |
ci | CI モード — 危険な文字が見つかった場合、非ゼロで終了 |
fix | ファイルからすべての双方向文字を削除(デフォルトは対話式) |
explain | 各双方向文字の働きを視覚的な例で表示 |
init | プロジェクト用の .bidi-guard.yml 設定ファイルを生成 |
| コードポイント | 名前 | 略称 | 深刻度 |
|---|
| U+200E | 左から右へのマーク | LRM | 低 |
| U+200F | 右から左へのマーク | RLM | 低 |
| U+061C | アラビア文字マーク | ALM | 低 |
| U+200D | ゼロ幅接合子 | ZWJ | 低 |
| U+200C | ゼロ幅非接合子 | ZWNJ | 低 |
| U+2066 | 左から右へのアイソレート | LRI | 中 |
| U+2067 | 右から左へのアイソレート | RLI | 高 |
| U+2068 | ファーストストロングアイソレート | FSI | 高 |
| U+2069 | ポップ方向アイソレート | PDI | 中 |
| U+202A | 左から右への埋め込み | LRE | 中 |
| U+202B | 右から左への埋め込み | RLE | 高 |
| U+202C | ポップ方向書式 | 中 | |
| U+202D | 左から右へのオーバーライド | LRO | 高 |
| U+202E | 右から左へのオーバーライド | RLO | 重大 |
| U+2028 | 行区切り | LS | 中 |
| U+2029 | 段落区切り | PS | 中 |