iOS/macOSとAndroid/Linuxの サンドボックス機構について調べた 2017/02/03 Kラボ部会発表資料 @hnw 1
前々回のあらすじ iOSアプリでfork(2)したい! なぜか無理 fork(2)の代替を探した 2
そもそもの疑問 ● 誰がfork(2)を無効化しているのか? ● どんな仕組みなのか? 3 「App Sandbox」が特定システムコールを無効化
本日の内容 ● iOS/macOSの「App Sandbox」 ○ アプリケーション用サンドボックス機構 ● Android/Linuxの「seccomp」 ○ システムコールを制限する仕組み ● どちらも情報が少ないので調査した ○ 注:chrootとかcgroupsとかの話はしません 4
話題1:App Sandbox (a.k.a. Seatbelt) ● iOSアプリの機能を制限する仕組み ● macOS上にも存在 ○ Mac OS X Lion(10.8)から導入 ○ iOS版のサブセットらしい 5
手元のmacOSで観察 6
手元のmacOSで実験 7 (「no-internet」の指定により、ネットワーク通信に関連するシステムコールが全て失敗する)
App Sandbox 概要 ● iOS/macOS上のsandbox環境 ○ storeアプリは全てsandbox配下 ● システムコールをフック ○ DSLでフィルタを記述 ● 構成 ○ カーネル拡張 ○ デーモン ○ ライブラリ 8 (iOS Hacker’s Handbook より引用)
sandboxに対するAppleのスタンス ● macOSアプリ ○ store審査でsandbox化必須 ○ GUIから設定する前提 ● iOSアプリ ○ 勝手にsandbox下で起動される ○ 開発者は対応作業なし ● 技術の詳細は非公開 ○ Cインターフェースが最近 deprecatedになった 9 (XcodeのmacOSアプリの設定)
sandbox_init(3) (deprecated) ● 権限を自ら捨てる ● 権限の詳細は「プロファイル」で指定 ● プロファイルの種類 ○ カスタムプロファイル ○ ビルトインプロファイル ● 実験コード:https://github.com/hnw/apple-sandbox-test 10
カスタムプロファイル ● SBPL (Sandbox Profile Language)で記述 ○ 許可・拒否のルールを記述するDSL ○ 内部的にはカスタムのScheme処理系で処理 ● 手元のmacOSにもある ○ /usr/share/sandbox/*.sb ○ /System/Library/Sandbox/Profiles/*.sb 11
カスタムプロファイルの文法 12 ● システムコールを複数束ね て許可・拒否を記述 ○ 例:「process-fork」 ● 引数でフィルタ指定可能 ○ 例:「file-read-data」 ○ 正規表現マッチも可能
ビルトインプロファイル ● 定義はsandboxd内に存在 ○ バイナリ化されており読み出しは困難 ○ 古いバージョンの定義は解析されている ● iOSアプリはビルトインプロファイル 「container」下で動作 ○ プロセス起動の禁止を実現している 13
App Sandboxまとめ ● システムコールをフィルタする仕組み ○ フィルタはDSLで定義、記述力は高い ● ファイルのアクセス制限も担当 ○ Linuxなら別の仕組み(SELinux)で実現するところ ● 開発環境やStore審査など仕組みで強制 ○ 開発者が自由に使うことは想定外? 14
話題2:seccomp ● システムコールのフィルタリング機構 ○ Linux 3.5から導入、多くの環境でデフォルト有効 ○ Android 7.0以降、全端末で有効 ○ バックエンドにBPFを利用 15
BPF (Barkley Packet Filter) ● パケットフィルタに特化したVM(?) ○ レジスタマシン(レジスタ数2) ○ フィルタとしてVM命令列を与える ○ JITコンパイルされるので高速、らしい →高速かつ記述力が高いのでseccompでも採用 16
BPFの例 17 ● フィルタ条件を記述 ● 大半の人類には難易度が高い (「LinuxのBPF : (1) パケットフィルタ - 睡分不足」より引用)
libseccomp ● seccompを扱いやすくするライブラリ ○ https://github.com/seccomp/libseccomp ○ 素のseccomp/BPFは使いたくないでござる ● 各言語のバインディングも存在 ○ Go / Perl / mruby ○ Python版はlibseccomp同梱 18
libseccompを試す(1) ● 実験コード ○ https://github.com/hnw/seccomp-test ● 利用の流れ ○ seccomp_init() :初期化 ○ seccomp_rule_add():ルール追加 ○ seccomp_release():ルールに従って権限を捨てる 19
libseccompを試す(2) ● 実際にコードを書いてみると結構面倒 ○ デフォルトdeny・必要分だけallowしていく ○ Cライブラリ関数の内部でどのシステムコールが呼ばれ るか自明でない →何度も実行して試行錯誤するしかない ○ プリセットの定義があれば楽なのになぁ… 20
seccompの能力(1) ● 任意のシステムコールをフック ● マッチした場合に次の処理ができる ○ 問答無用でプロセスごとKILL ○ シグナルを投げる ■ シグナルハンドラで任意の処理を行う ○ 任意のerrnoを返す 21
seccompの能力(2) ● syscall引数(64bit int)の値による分岐 ○ EQ / NE / LE / GE / MASKED_EQ など ■ 例:open()でO_WRONLYが指定されたらKILL ○ 文字列比較はできない 22
seccompの適用例 ● 権限を捨ててから危険な処理を行う ○ 例:Chrome 20からFlash pluginがseccomp下で動作 ○ 脆弱性があった場合の被害を最小化する目的 ○ 3rd partyモジュールを実行するような場合に最適 23
Android 7.0とseccomp ● 現状、大多数のアプリとseccompは無関係 ○ AOSPを見てもほとんど使われていない ○ App Sandboxのような利用は現時点では見られない ● 使いたい人が使えるようにしたという理解 ○ 今のところChromeくらい 24
まとめ(1) ● 「sandbox的な機構が両OSにあるぞ!」と思っ て調べてみたら運用方針が全く違った ○ iOS/macOS:3rd partyアプリの不正を防ぐ、強制 ○ Android/Linux:安全性向上の仕組みを提供、任意 ● 優劣の話ではなく、役割が違う ○ Androidだとファイルアクセス制御はSELinuxが担当 25
まとめ(2) ● SELinuxは今後も現役、seccompと補完関係 ○ 調べる前はSELinuxを殺しに来たかと思った ○ SELinux:管理者が頑張る・ファイルアクセス特化 ○ seccomp:開発者が頑張る・細かい制御は不向き 26
資料1 27 セキュリティ系の書籍 2012年発行 かなり攻撃者目線で、 日本では発売できない印象
資料2 28 Ruxcon 2014での発表資料 iOS8のApp Sandbox詳細
29 完

iOS/macOSとAndroid/Linuxのサンドボックス機構について調べた