Skip to content

hal0taso/linux_kernel_security

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

59 Commits
 
 
 
 
 
 
 
 
 
 

Repository files navigation

linux_kernel_security

for self-educating and seccamp 2017

第1章:ユーザ空間でC言語プログラミングについて体験する。(1時間)

  1. ユーザ空間プログラムで Hello world. を実現する。[DONE]

    • 必要なパッケージのインストールができることを確認する。
    • strace / ltrace で動作を追跡し、ライブラリ関数( printf fwrite )とシステムコール( write )との差異を確認する。
  2. 無限ループやデッドロック状態を体験する。[DONE]

    • マルチスレッド( pthread mutex )ではなくマルチプロセス( flock )を使用する。
    • pidof でプロセスIDを確認し、 SIGKILL で強制終了できることを確認する。
    • カーネル内はマルチスレッドなので本当はマルチスレッドの方がよい?
    • でも、マルチスレッドな時点で苦労するのが目に見えているので、マルチプロセスで行く。
  3. NULL pointer deref でクラッシュさせる。[DONE]

    • プロセスが終了するだけで済むことを確認する。
  4. 0除算でクラッシュさせる。[DONE]

    • プロセスが終了するだけで済むことを確認する。
    • この講義としては必須ではないが、簡単に確認できるので入れておく?
  5. スタック変数を大量に使う。[DONE]

    • スタック変数を自由に使えることを知る。
  6. 連続したメモリを割り当てる。[DONE]

    • 連続したメモリを自由に割り当てられることを知る。
  7. メモリリークでクラッシュさせる。[DONE]

    • OOM killer によりプロセスが強制終了するだけで済むことを確認する。

問題が起きたら SIGKILL で強制終了させることができるので、影響範囲を限定できる。
基本的にリソースはプロセスの終了により自動的に解放されるので、
リソースのリークが原因でシステム全体がダウンすることは無い。

第2章:カーネル空間ではいろいろと違うことを体験する。(2時間)

  1. カーネルモジュールで Hello world. を実現する。

    • 必要なパッケージのインストールができることを確認する。
    • module_init で printk() を呼ぶ。
  2. 無限ループや待ち状態を体験する。

    • SIGKILL で強制終了できないことを確認する。
    • mutex_lock() と mutex_lock_killable() の差異について知る。
    • module_init で double lock する?
  3. NULL pointer deref でクラッシュさせる。

    • システムがダウンしてしまうことを確認する。
    • /proc/sys/kernel/panic_on_oops の設定に依存する。
  4. 0除算でクラッシュさせる。

    • システムがダウンしてしまうことを確認する。
  5. スタック変数を大量に使う。

    • スタック変数を自由に使えないことを知る。
  6. 連続したメモリを割り当てる。

    • 連続したメモリを自由に割り当てられないことを知る。
  7. メモリリークでクラッシュさせる。

    • カーネル内でのメモリリークが危険なことを知る。
    • ユーザ空間からカーネルメモリリーク攻撃される可能性の一例 keyctl OOM DoS
    • 多数の無実なプロセスを殺してしまう OOM killer 。

カーネルは究極のマルチスレッドプログラム。システムをシャットダウンまたは
再起動するまで動き続けるため、リソース管理が大変。いろいろな制約がある。
だから、ユーザ空間でできることはユーザ空間でやろう。ユーザ空間からの
攻撃とカーネル空間内のバグに注意しながら。

第3章: clamav を試す。(2時間)

  1. FUSE について知る。
  • clamfs を試す。 git からコンパイルする? tarball からコンパイルする?
  1. libclam のAPI呼び出しを使う。

    • APIを意識した練習をする。
    • テンプレをベースに、ユーザ空間内でのやりとりの練習をする。
  2. 動作確認をする。

    • 無害な検体を用意できると嬉しい。

準備完了。これからが本題です。

第4章:LSMから clamav を呼び出す。(5時間)

  1. AKARI について知る。

    • カーネルモジュールからLSMを呼び出すための方法。テンプレで済ませる。
  2. execve をフックする。

    • パス名の計算方法を知り、実行が要求されたプログラムのパス名を表示する。
    • 動的メモリ割り当てを使うには?
  3. 対話的に確認できるようにする。

    • ユーザ空間とのやり取りは結構面倒。時間がかかると思われる。

フックまでは事前学習で体験させておきたいので、ここまでを事前学習(10時間)で済ませる。
ここから先を当日の内容(4時間)として行う。

  1. LSMの歴史について知る。

    • LKM非対応化について。
    • カーネルモジュールからLSMを使う AKARI の話。
  2. ユーザ空間のプログラムを書く。

    • カーネルからパス名を受け取り、API経由で clamd に渡し、
    • 結果を確認してからカーネルに返事をする。
      • 名前空間は扱わない。
      • 再帰呼び出しをどうする?
      • execve だけなら気にしない?
  3. 動作確認をする。

    • 無害な検体を用意できると嬉しい。
  4. 最新の話をする。

    • ro_after_init の話について。
    • vmsplice では SELinux を無効化できた。
    • per task_struct blob の復活について。
    • 他のモジュールが提案されている話について。
  5. Q&A?