概要
- Fil-C はC/C++のソースコードを改変せずに メモリ安全性 を実現するコンパイラ
- 既存アプリケーション のメモリ安全化に特化した「徹底的な互換性」志向
- 独自ABI・GC・信号安全 など多彩な安全機構を搭載
- パフォーマンス改善 が進み、実用性が向上
- Linux From Scratch でのメモリ安全ユーザー空間構築実績あり
Fil-C:C/C++のためのメモリ安全なコンパイラ
- Fil-C はCやC++のコードを 無改変でメモリ安全 に実行可能にするコンパイラ
- ポインタ演算、共用体 など従来メモリ安全言語で問題視される機能もサポート
- 「 fanatically compatible」を掲げ、既存C/C++資産の再利用を重視
- 開発者は Filip Pizlo 氏一人だが、 Linuxユーザー空間全体 のビルドに成功
- 信号処理の安全化 や 並行ガーベジコレクタ も実装
- Clang をベースにしたフォークで、 Apache v2.0 ライセンス(LLVM例外付与)
性能と互換性
- 初期実装は 著しく遅かった が、最適化により Clang比数倍の遅さ に改善
- Bash 5.2.32 をFil-Cでビルドし実用テストした結果、体感的な遅延は少ない
- 内部ABIが独自 のため、Fil-Cでビルドしたオブジェクトは他コンパイラとリンク不可
- ソースレベル互換性 を維持しつつ、 全てFil-Cで再ビルド が必要
- Rustなど他言語との相互リンク は未対応
ポインタ管理とInvisiCaps
- C言語のメモリ安全化 最大の課題は ポインタ管理
- 当初は 256ビット非スレッドセーフなポインタ を採用していたが、現行は InvisiCaps方式
- InvisiCaps は「 能力(capability)」と「 アドレス」を分離管理
- プログラムからは 通常の64ビットポインタ に見える
- 実際には 補助情報(aux word) を別領域に格納
- ヒープ確保時 にオブジェクト直前へ 上限値・aux word の2つのメタデータを付加
- ポインタ書き込み時 に補助領域を確保・能力情報を管理
- 構造体内ポインタ は実メモリ使用量が 2倍 になる
- ポインタ読み書きごとに間接参照 が必要なため、 性能は4倍程度低下 (用途に依存)
- _Atomicやvolatile 対応のため、128ビット領域を活用し アトミック操作 を実現
- aux word にタグ情報を付加し、関数・スレッド・mmap領域や解放済みオブジェクトの識別も可能
メモリ管理とGC
- オブジェクト解放時、 aux wordで即時解放 を可能に
- 本体メモリはGCで遅延解放 し、 use-after-free の検出を徹底
- 補助情報により正確な到達性解析 を実現し、 Boehm GC より精緻な管理
- 並行・並列GC を採用し、 スレッド停止時間を最小化
- safe point でGCとスレッド同期
- ループ等の 逆方向制御フロー ごとにsafe pointを挿入
- 通常時はフラグチェックのみ、GC要求時のみコールバック処理
- signal handler もsafe point到達時のみ実行し、 malloc等もsignal-safe を保証
メモリ安全なLinuxユーザー空間
- Linux From Scratch (LFS) の手順で メモリ安全なユーザー空間 を構築可能
- Fil-C自身のランタイムやglibc、カーネル は非Fil-Cでビルドが必要
- LFSの 第7章まで は通常通り、以降Fil-Cで クロスビルドツール を構築
- Fil-C付属の 自動化スクリプト でGUIやEmacs等の複雑なアプリもビルド可能
- 既存Cプログラムのメモリ安全化 において、 実用的なソリューション を提供
適用の検討
- 未定義動作全般 への対策はないが、 メモリ安全性関連の脆弱性 対策に有効
- 安定性や成熟度 には課題が残るが、 パフォーマンスより安全性重視 の用途に最適
- 初期の性能問題で導入を断念した層 も、再評価の価値あり