Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.
ライブマイグレーション実装で
体験したデバッグの解説
深井 貴明(筑波大学),竹腰 開(筑波大学), 品川 高廣(東京大学)
発表趣旨
• ライブマイグレーションの実装中に難しいデバッグ
• 状態を移す時に様々なマシン状態を壊してしまう
• Panic も起こさず,ログがでないとデバッグが難しい
• 同じ悲劇を他所で見ないために情報を共有
Table of Contents
• ライブマイグレーションの実装について
• Case 1: Init プロセスがSegV
• Case 2: Linux が静かにブートしない
• Case 3: Triple Fault
• Case 4...
Table of Contents
• ライブマイグレーションの実装について
• Case 1: Init プロセスがSegV
• Case 2: Linux が静かにブートしない
• Case 3: Triple Fault
• Case 4...
ライブマイグレーション
Hardware
BitVisor BitVisor
OS
Hardware
OS
BitVisor が物理ハードウェアの状態を取得&復元
移動先マシン移動元マシン
実装環境
OS
• Debian 7.8 (32bit, 64bit)
• Linux 3.2.65
マシン
• CPU: Core i7 4790K (シングルコア 利用)
• NIC: Realtek 8169
• 割り込みコントローラ: ...
Table of Contents
• ライブマイグレーションの実装について
• Case 1: Init プロセスがSegV
• Case 2: Linux が静かにブートしない
• Case 3: Triple Fault
• Case 4...
Case1: Init プロセスがSegV
• マイグレーションすると init プロセスが死ぬ
• Linux, BitVisor ともにpanic なし
Init: PANIC: segmentation violation at 0xb7...
原因究明
• violation を起こしたアドレスをみるとどうもlibc の中
• アドレスランダマイズを無効化
• ブートオプション norandmaps
• apt-get でデバッグシンボル付きのglibc を入手
• addr2lin...
問題の命令は…
•xor %%xmm0 %%xmm0 で落ちてた
原因
• SIMD の状態の整合がとれてなかった
• SIMD の状態
• fxstore
• CR4
• XCR0
• xor でSegV って…
Case2: SSE 機能を隠すとLinuxが
ブートしない
• BitVisor でCPUID のSIMD関連のフラグをすべてクリア
• GRUB は起動する
• Linux の起動を始めると何も出力されずに止まる
原因究明
• Linux がメッセージを出す前に止まる
 ブート初期のコードのどこかで止まる
• CPUIDの挙動を変えて落ちる
 CPUID の結果を使っているコードを探す
64 bit Linux はSIMD 必須 らしい
• 64 bit Linux はブートの初期段階でCPUがSIMDに
対応しているかチェックする
• もしなかったら,hlt してた
arch/x86/kernel/verify_cpu.S
verify_cpu:
(中略)
verify_cpu_sse_test:
movl $1,%eax
cpuid
andl $SSE_MASK,%edx
cmpl $SSE_MASK,%...
arch/x86/kernel/trampoline_64.S
call verify_cpu # Verify the cpu supports long mode
testl %eax, %eax # Check for return co...
余談:
本当にこのSSE のverify 必要?
SIMD の状態を転送は大変そうだったので
手抜き実装を試す
• ブート初期の起動時だけCPUIDはSSEを見せる
• 命令アドレスはわかっているので,RIP見て判断
• これでも動いた
• ...
Case 3: Triple Fault
• Linux がTriple Fault
• Triple Fault は何も手掛かりがない
原因究明
• ダメ元でpanic のログなどでググってみる
• 似てような現象についての議論をLKMLで見つける
• どうもsysenter がおかしくなるとそういうことになる
らしい
原因
• 32bit Linux と64bit Linux とのシステムコール方式
の違いに対応してなかった
• 32bit はソフトウェア割り込み,64bitはsysenter
• sysenter 関係の状態送っていない
Table of Contents
• Case 1: Init プロセスがSegV
• Case 2: Linux が静かにブートしない
• Case 3: Triple Fault
• Case 4: 止まるが動く
• Case 5: Pr...
Case 4: 動くけど止まる
• マイグレーション後に止まる
• キーを押下すると動く
• がすぐ止まる
• キーを押すたびに少し動く
• Panic はしない
原因
• Timer 割り込みの停止
• タイマ割り込みが止まるとスケジューリングも止ま
る
• 何か割り込みがあるとスケジューリングする(ように
見える)
Table of Contents
• Case 1: Init プロセスがSegV
• Case 2: Linux が静かにブートしない
• Case 3: Triple Fault
• Case 4: 止まるが動く
• Case 5: Pr...
Case 5: Preempt Timer
Intel VT には定期的にVMExit を発生させるPreempt
Timer という機能がある
これを使おうとしたら…
• 設定した間隔でVMExitしない
• 頻度が異常に小さい
• コマンド...
原因究明
• この機能を使うVMMが見当たらない
• 唯一のドキュメントはIntel SDM だけ
片っ端からSDM を読む
原因
• Preempt Timer のタイマはC2以上のステートで止
まる
• どうやって使うのがいいんだろうか…?
Table of Contents
• Case 1: Init プロセスがSegV
• Case 2: Linux が静かにブートしない
• Case 3: Triple Fault
• Case 4: 止まるが動く
• Case 5: Pr...
Case 6: RTL 8169 ドライバで固まる
Realtek の受信ディスクリプタの調整
OS が静かにとまる
(Linux, BitVisor, ともにpanicせず)
正常なRTL8169 のリングバッファ
OWN bit その他
NIC
NIC
Host 受信したパケットに関する情報
Host 受信したパケットに関する情報
NIC
NIC
NIC
Head
pointer
Tail
pointer
OS
ド...
静かに止まった原因
• Head ポインタがTail ポインタを追い越した
• Realtek が無限に割り込みを飛ばしてくる
• 割り込みでDoS
• 1コアしか動かしてなく,他に動くコアがない
Tailが追い越したとき
OWN bit その他
NIC
NIC
Host 受信したパケットに関する情報
Host 受信したパケットに関する情報
NIC
NIC
NIC
Tail
pointer
ドライバ側 Head
pointer
空ディスク...
RTL8169は割り込みを出すが….
Hardware
BitVisor
空ディスクリプタがない
割り込み
RTL8169は割り込みを出すが….
Hardware
BitVisor
空ディスクリプタがない
無視
割り込み
因果関係まとめ
原因 結果
SIMDを壊す Init プロセスがSegV
64bit Linux でSSE を隠す ブートしない
SYSENTER_*_MSR を壊す Triple Fault
Timer 割り込みが止まる 動いたり止まったりす...
まとめ
• マイグレーション実装時に体験したデバッグを説明
• 皆さんのデバッグに役に立てば幸いです
Upcoming SlideShare
Loading in …5
×

ライブマイグレーション実装で体験したデバッグの解説

739 views

Published on

2015年11月26日 BitVisor Summit 4

Published in: Technology
  • Be the first to comment

ライブマイグレーション実装で体験したデバッグの解説

  1. 1. ライブマイグレーション実装で 体験したデバッグの解説 深井 貴明(筑波大学),竹腰 開(筑波大学), 品川 高廣(東京大学)
  2. 2. 発表趣旨 • ライブマイグレーションの実装中に難しいデバッグ • 状態を移す時に様々なマシン状態を壊してしまう • Panic も起こさず,ログがでないとデバッグが難しい • 同じ悲劇を他所で見ないために情報を共有
  3. 3. Table of Contents • ライブマイグレーションの実装について • Case 1: Init プロセスがSegV • Case 2: Linux が静かにブートしない • Case 3: Triple Fault • Case 4: 止まるが動く • Case 5: Preempt Timer • Case 6: RTL 8169 ドライバが止まる
  4. 4. Table of Contents • ライブマイグレーションの実装について • Case 1: Init プロセスがSegV • Case 2: Linux が静かにブートしない • Case 3: Triple Fault • Case 4: 止まるが動く • Case 5: Preempt Timer • Case 6: RTL 8169 ドライバが止まる
  5. 5. ライブマイグレーション Hardware BitVisor BitVisor OS Hardware OS BitVisor が物理ハードウェアの状態を取得&復元 移動先マシン移動元マシン
  6. 6. 実装環境 OS • Debian 7.8 (32bit, 64bit) • Linux 3.2.65 マシン • CPU: Core i7 4790K (シングルコア 利用) • NIC: Realtek 8169 • 割り込みコントローラ: PIC, IOAPIC • タイマ: PIT
  7. 7. Table of Contents • ライブマイグレーションの実装について • Case 1: Init プロセスがSegV • Case 2: Linux が静かにブートしない • Case 3: Triple Fault • Case 4: 止まるが動く • Case 5: Preempt Timer • Case 6: RTL 8169 ドライバが止まる
  8. 8. Case1: Init プロセスがSegV • マイグレーションすると init プロセスが死ぬ • Linux, BitVisor ともにpanic なし Init: PANIC: segmentation violation at 0xb7759f2d! sleeping for 30 seconds
  9. 9. 原因究明 • violation を起こしたアドレスをみるとどうもlibc の中 • アドレスランダマイズを無効化 • ブートオプション norandmaps • apt-get でデバッグシンボル付きのglibc を入手 • addr2line やobjdump で問題の命令を特定する
  10. 10. 問題の命令は… •xor %%xmm0 %%xmm0 で落ちてた
  11. 11. 原因 • SIMD の状態の整合がとれてなかった • SIMD の状態 • fxstore • CR4 • XCR0 • xor でSegV って…
  12. 12. Case2: SSE 機能を隠すとLinuxが ブートしない • BitVisor でCPUID のSIMD関連のフラグをすべてクリア • GRUB は起動する • Linux の起動を始めると何も出力されずに止まる
  13. 13. 原因究明 • Linux がメッセージを出す前に止まる  ブート初期のコードのどこかで止まる • CPUIDの挙動を変えて落ちる  CPUID の結果を使っているコードを探す
  14. 14. 64 bit Linux はSIMD 必須 らしい • 64 bit Linux はブートの初期段階でCPUがSIMDに 対応しているかチェックする • もしなかったら,hlt してた
  15. 15. arch/x86/kernel/verify_cpu.S verify_cpu: (中略) verify_cpu_sse_test: movl $1,%eax cpuid andl $SSE_MASK,%edx cmpl $SSE_MASK,%edx je verify_cpu_sse_ok test %di,%di jz verify_cpu_no_longmode # only try to force SSE on AMD (中略) verify_cpu_no_longmode: popfl # Restore caller passed flags movl $1,%eax ret
  16. 16. arch/x86/kernel/trampoline_64.S call verify_cpu # Verify the cpu supports long mode testl %eax, %eax # Check for return code jnz no_longmode (中略) no_longmode: hlt jmp no_longmode
  17. 17. 余談: 本当にこのSSE のverify 必要? SIMD の状態を転送は大変そうだったので 手抜き実装を試す • ブート初期の起動時だけCPUIDはSSEを見せる • 命令アドレスはわかっているので,RIP見て判断 • これでも動いた • 何のためのverify なんだ?
  18. 18. Case 3: Triple Fault • Linux がTriple Fault • Triple Fault は何も手掛かりがない
  19. 19. 原因究明 • ダメ元でpanic のログなどでググってみる • 似てような現象についての議論をLKMLで見つける • どうもsysenter がおかしくなるとそういうことになる らしい
  20. 20. 原因 • 32bit Linux と64bit Linux とのシステムコール方式 の違いに対応してなかった • 32bit はソフトウェア割り込み,64bitはsysenter • sysenter 関係の状態送っていない
  21. 21. Table of Contents • Case 1: Init プロセスがSegV • Case 2: Linux が静かにブートしない • Case 3: Triple Fault • Case 4: 止まるが動く • Case 5: Preempt Timer • Case 6: RTL 8169 ドライバが止まる
  22. 22. Case 4: 動くけど止まる • マイグレーション後に止まる • キーを押下すると動く • がすぐ止まる • キーを押すたびに少し動く • Panic はしない
  23. 23. 原因 • Timer 割り込みの停止 • タイマ割り込みが止まるとスケジューリングも止ま る • 何か割り込みがあるとスケジューリングする(ように 見える)
  24. 24. Table of Contents • Case 1: Init プロセスがSegV • Case 2: Linux が静かにブートしない • Case 3: Triple Fault • Case 4: 止まるが動く • Case 5: Preempt Timer • Case 6: RTL 8169 ドライバが止まる
  25. 25. Case 5: Preempt Timer Intel VT には定期的にVMExit を発生させるPreempt Timer という機能がある これを使おうとしたら… • 設定した間隔でVMExitしない • 頻度が異常に小さい • コマンドを実行するとVMExit が発生
  26. 26. 原因究明 • この機能を使うVMMが見当たらない • 唯一のドキュメントはIntel SDM だけ 片っ端からSDM を読む
  27. 27. 原因 • Preempt Timer のタイマはC2以上のステートで止 まる • どうやって使うのがいいんだろうか…?
  28. 28. Table of Contents • Case 1: Init プロセスがSegV • Case 2: Linux が静かにブートしない • Case 3: Triple Fault • Case 4: 止まるが動く • Case 5: Preempt Timer • Case 6: RTL 8169 ドライバが止まる
  29. 29. Case 6: RTL 8169 ドライバで固まる Realtek の受信ディスクリプタの調整 OS が静かにとまる (Linux, BitVisor, ともにpanicせず)
  30. 30. 正常なRTL8169 のリングバッファ OWN bit その他 NIC NIC Host 受信したパケットに関する情報 Host 受信したパケットに関する情報 NIC NIC NIC Head pointer Tail pointer OS ドライバ側
  31. 31. 静かに止まった原因 • Head ポインタがTail ポインタを追い越した • Realtek が無限に割り込みを飛ばしてくる • 割り込みでDoS • 1コアしか動かしてなく,他に動くコアがない
  32. 32. Tailが追い越したとき OWN bit その他 NIC NIC Host 受信したパケットに関する情報 Host 受信したパケットに関する情報 NIC NIC NIC Tail pointer ドライバ側 Head pointer 空ディスクリプタがない OS
  33. 33. RTL8169は割り込みを出すが…. Hardware BitVisor 空ディスクリプタがない 割り込み
  34. 34. RTL8169は割り込みを出すが…. Hardware BitVisor 空ディスクリプタがない 無視 割り込み
  35. 35. 因果関係まとめ 原因 結果 SIMDを壊す Init プロセスがSegV 64bit Linux でSSE を隠す ブートしない SYSENTER_*_MSR を壊す Triple Fault Timer 割り込みが止まる 動いたり止まったりする C2ステート異常に落ちる Preempt Timer が止まる RTL8169のRXリングバッファの Tail がHead を追い抜く 静かに止まる
  36. 36. まとめ • マイグレーション実装時に体験したデバッグを説明 • 皆さんのデバッグに役に立てば幸いです

×