第673回の
デバッグパッケージのインストール
第673回では、
最初に行うべきなのは、
というわけで第673回で取得した、crash
コマンドを利用します。crashはカーネルダンプの調査に特化した、
ただしカーネルをデバッガで調査するのであれば、
$ sudo apt install ubuntu-dbgsym-keyring $ sudo tee /etc/apt/sources.list.d/ddebs.list << EOF deb http://ddebs.ubuntu.com/ $(lsb_release -cs) main restricted universe multiverse deb http://ddebs.ubuntu.com/ $(lsb_release -cs)-updates main restricted universe multiverse deb http://ddebs.ubuntu.com/ $(lsb_release -cs)-proposed main restricted universe multiverse EOF $ sudo apt update
ちなみに上記はUbuntu 18.
さて、
$ sudo apt install linux-image-$(uname -r)-dbgsym
おそらく1GiBほどのサイズをダウンロードすることになるので注意してください。またクラッシュダンプ取得時のカーネルバージョンが、$(uname -r)
」
[ 6262.530045] CPU: 3 PID: 111191 Comm: tee Kdump: loaded Tainted: G S C E 5.11.0-22-generic #23-Ubuntu
ここの5.
」$(uname -r)
」
ちなみにcrashコマンドとデバッグパッケージさえ用意できるなら、
なお、
クラッシュダンプの解析
crashコマンドを使ってクラッシュダンプを解析するには/usr/
」
$ crash /usr/lib/debug/boot/vmlinux-5.11.0-22-generic /var/crash/202107040335/dump.202107040335 crash 7.2.9 (中略) GNU gdb (GDB) 7.6 (中略) KERNEL: /usr/lib/debug/boot/vmlinux-5.11.0-22-generic DUMPFILE: 202107040335/dump.202107040335 [PARTIAL DUMP] CPUS: 4 DATE: Sun Jul 4 03:34:41 JST 2021 UPTIME: 00:29:50 LOAD AVERAGE: 0.38, 0.18, 0.09 TASKS: 475 NODENAME: ubuntu-ax2 RELEASE: 5.11.0-22-generic VERSION: #23-Ubuntu SMP Thu Jun 17 00:34:23 UTC 2021 MACHINE: x86_64 (1695 Mhz) MEMORY: 3.9 GB PANIC: "Kernel panic - not syncing: sysrq triggered crash" PID: 111191 COMMAND: "tee" TASK: ffff8b4702b3b080 [THREAD_INFO: ffff8b4702b3b080] CPU: 3 STATE: TASK_RUNNING (PANIC) crash>
第一引数がvmlinuxファイルで、
crashをうまく起動できたら、
crash> bt PID: 111191 TASK: ffff8b4702b3b080 CPU: 3 COMMAND: "tee" #0 [ffffa2cd898cfc80] machine_kexec at ffffffffa1a77b63 #1 [ffffa2cd898cfce0] __crash_kexec at ffffffffa1b66a42 #2 [ffffa2cd898cfdb0] panic at ffffffffa25dd1a3 #3 [ffffa2cd898cfe30] sysrq_handle_crash at ffffffffa2160bfa #4 [ffffa2cd898cfe40] __handle_sysrq.cold at ffffffffa26094b6 #5 [ffffa2cd898cfe78] write_sysrq_trigger at ffffffffa21615f8 #6 [ffffa2cd898cfe90] proc_reg_write at ffffffffa1dcc6ca #7 [ffffa2cd898cfeb0] vfs_write at ffffffffa1d1eb76 #8 [ffffa2cd898cfee8] ksys_write at ffffffffa1d21277 #9 [ffffa2cd898cff28] __x64_sys_write at ffffffffa1d2130a #10 [ffffa2cd898cff38] do_syscall_64 at ffffffffa2636ab8 #11 [ffffa2cd898cff50] entry_SYSCALL_64_after_hwframe at ffffffffa280008c RIP: 00007f3a4110cc27 RSP: 00007ffeb514fbd8 RFLAGS: 00000246 RAX: ffffffffffffffda RBX: 0000000000000002 RCX: 00007f3a4110cc27 RDX: 0000000000000002 RSI: 00007ffeb514fcc0 RDI: 0000000000000003 RBP: 00007ffeb514fcc0 R8: 0000000000000002 R9: 0000000000000001 R10: 00000000000001b6 R11: 0000000000000246 R12: 0000000000000002 R13: 00005622844eb4e0 R14: 0000000000000002 R15: 00007f3a411e68a0 ORIG_RAX: 0000000000000001 CS: 0033 SS: 002b crash>
このあたりはdmesgで表示されているものと同じですね。タスクのリストはpsコマンドで確認できます。
crash> ps PID PPID CPU TASK ST %MEM VSZ RSS COMM > 0 0 0 ffffffffa361a940 RU 0.0 0 0 [swapper/0] > 0 0 1 ffff8b4800a81840 RU 0.0 0 0 [swapper/1] 0 0 2 ffff8b4800a86100 RU 0.0 0 0 [swapper/2] 0 0 3 ffff8b4800a848c0 RU 0.0 0 0 [swapper/3] 1 0 1 ffff8b4800276100 IN 0.2 165012 11152 systemd (中略) 3755 3746 1 ffff8b4727169840 IN 1.2 496448 57560 dconf worker 3761 3750 0 ffff8b47029a8000 IN 0.1 19476 3928 tmux: client > 3797 3191 2 ffff8b4702b2b080 RU 0.1 20136 4244 tmux: server 3805 3797 3 ffff8b47029ab080 IN 0.1 21328 6076 bash (中略) 110886 3191 2 ffff8b4727766100 IN 0.5 372332 23340 pool-tracker-st 111190 3805 1 ffff8b473b840000 IN 0.1 24104 6004 sudo > 111191 111190 3 ffff8b4702b3b080 RU 0.0 18008 2048 tee
「>
」
crash> bt 3797 PID: 3797 TASK: ffff8b4702b2b080 CPU: 2 COMMAND: "tmux: server" #0 [ffffa2cd8127fe88] crash_nmi_callback at ffffffffa1a6a997 #1 [ffffa2cd8127fe98] nmi_handle at ffffffffa1a38d29 #2 [ffffa2cd8127fee8] default_do_nmi at ffffffffa2638367 #3 [ffffa2cd8127ff18] exc_nmi at ffffffffa26385db #4 [ffffa2cd8127ff50] asm_exc_nmi at ffffffffa28014c3 RIP: 00007f989b16aad9 RSP: 00007ffd8ceb0590 RFLAGS: 00000206 RAX: 0000563e6009d430 RBX: 0000000000000000 RCX: 0000000000000000 RDX: 0000000000000000 RSI: 0000000000000000 RDI: 0000000000000000 RBP: 0000563e600f3468 R8: 0000000000000003 R9: 0000000000000001 R10: 0000000000000003 R11: 0000000000000000 R12: 0000563e600f3468 R13: 0000000000000000 R14: 0000563e600f3468 R15: 0000563e6009d430 ORIG_RAX: ffffffffffffffff CS: 0033 SS: 002b crash> task 3797 PID: 3797 TASK: ffff8b4702b2b080 CPU: 2 COMMAND: "tmux: server" struct task_struct { thread_info = { flags = 0, syscall_work = 0, status = 0 }, (後略)
psやtaskのように行数が多い場合はページャー経由での表示になります。もしページャーを無効化したい場合はset scroll off
」
グローバル変数などはpコマンドで内容を確認できます。またアドレスがわかっていれば、
crash> p jiffies jiffies = $1 = 4296457959 crash> p vermagic vermagic = $2 = "5.11.0-22-generic SMP mod_unload modversions "
タスクごとのファイルディスクリプター一覧は次のように確認できます。
crash> files 732 PID: 732 TASK: ffff8b480defb080 CPU: 2 COMMAND: "NetworkManager" ROOT: / CWD: / FD FILE DENTRY INODE TYPE PATH 0 ffff8b480d2b7f00 ffff8b4800462240 ffff8b48010cd420 CHR /dev/null 1 ffff8b48077a3600 ffff8b4803c15180 ffff8b48085fca40 SOCK UNIX 2 ffff8b48077a3600 ffff8b4803c15180 ffff8b48085fca40 SOCK UNIX 3 ffff8b48077ef500 ffff8b4803c689c0 ffff8b4801a98be0 UNKN [eventfd] 4 ffff8b4807b09b00 ffff8b4803d04480 ffff8b4801a98be0 UNKN [eventfd] 5 ffff8b4807b09600 ffff8b4803d046c0 ffff8b4803d46e00 SOCK UNIX 6 ffff8b4807339300 ffff8b4803c47d80 ffff8b4803d44080 SOCK UNIX 7 ffff8b48023e3300 ffff8b4803d603c0 ffff8b4801a98be0 UNKN [eventfd] 8 ffff8b480735b800 ffff8b4803ce5b40 ffff8b4803ba84c0 REG / 9 ffff8b480735be00 ffff8b4803cfe480 ffff8b4803c1b1e0 REG / 10 ffff8b48073aff00 ffff8b4803cfea80 ffff8b4803d26ac0 SOCK NETLINK 11 ffff8b48073af100 ffff8b4803cfe840 ffff8b4803d25a80 SOCK NETLINK 12 ffff8b48073af300 ffff8b4803cfeb40 ffff8b4803d26780 SOCK NETLINK 13 ffff8b480c344700 ffff8b4803d67180 ffff8b4801a98be0 UNKN inotify 14 ffff8b4809f39900 ffff8b4803d67c00 ffff8b4801a98be0 UNKN inotify 15 ffff8b480dc0c100 ffff8b473c5ecd80 ffff8b480e2cca40 SOCK NETLINK 16 ffff8b473c100a00 ffff8b473c5ed000 ffff8b473c64ca40 SOCK NETLINK 17 ffff8b470289e700 ffff8b4703c57b40 ffff8b4801a98be0 UNKN [eventpoll] 18 ffff8b4809205500 ffff8b473c7fe180 ffff8b47396048e0 FIFO /run/systemd/inhibit/systemd/inhibit/3.ref 19 ffff8b4702b61900 ffff8b4714818600 ffff8b4801a98be0 UNKN [eventpoll] 20 ffff8b4702b61200 ffff8b47148189c0 ffff8b4801a98be0 UNKN [timerfd] 21 ffff8b4719513700 ffff8b473c749e40 ffff8b47149d2e00 SOCK RAWv6 22 ffff8b4702b61700 ffff8b4714818f00 ffff8b473c785dc0 SOCK UDPv6 23 ffff8b4702b61800 ffff8b4714818540 ffff8b473c784a40 SOCK PACKET 24 ffff8b473c39d700 ffff8b4720aab180 ffff8b473c786440 SOCK UDP 25 ffff8b471ce4da00 ffff8b4714baaa80 ffff8b4801a98be0 UNKN [timerfd]
crashでは他にもさまざまなコマンドで、
ソースコードも参照できるようにする
GDBと同じように、
crash> dis write_sysrq_trigger 0xffffffffa21615d0 <write_sysrq_trigger>: nopl 0x0(%rax,%rax,1) [FTRACE NOP] 0xffffffffa21615d5 <write_sysrq_trigger+5>: push %rbp 0xffffffffa21615d6 <write_sysrq_trigger+6>: mov %rsp,%rbp 0xffffffffa21615d9 <write_sysrq_trigger+9>: push %rbx 0xffffffffa21615da <write_sysrq_trigger+10>: mov %rdx,%rbx 0xffffffffa21615dd <write_sysrq_trigger+13>: test %rdx,%rdx 0xffffffffa21615e0 <write_sysrq_trigger+16>: je 0xffffffffa21615f8 <write_sysrq_trigger+40> 0xffffffffa21615e2 <write_sysrq_trigger+18>: mov %rsi,%rax 0xffffffffa21615e5 <write_sysrq_trigger+21>: callq 0xffffffffa20238f0 <__get_user_1> 0xffffffffa21615ea <write_sysrq_trigger+26>: test %eax,%eax 0xffffffffa21615ec <write_sysrq_trigger+28>: jne 0xffffffffa2161601 <write_sysrq_trigger+49> 0xffffffffa21615ee <write_sysrq_trigger+30>: movsbl %dl,%edi 0xffffffffa21615f1 <write_sysrq_trigger+33>: xor %esi,%esi 0xffffffffa21615f3 <write_sysrq_trigger+35>: callq 0xffffffffa2161110 <__handle_sysrq> 0xffffffffa21615f8 <write_sysrq_trigger+40>: mov %rbx,%rax 0xffffffffa21615fb <write_sysrq_trigger+43>: mov -0x8(%rbp),%rbx 0xffffffffa21615ff <write_sysrq_trigger+47>: leaveq 0xffffffffa2161600 <write_sysrq_trigger+48>: retq 0xffffffffa2161601 <write_sysrq_trigger+49>: mov $0xfffffffffffffff2,%rax 0xffffffffa2161608 <write_sysrq_trigger+56>: jmp 0xffffffffa21615fb <write_sysrq_trigger+43> 0xffffffffa216160a <write_sysrq_trigger+58>: int3 0xffffffffa216160b <write_sysrq_trigger+59>: int3 0xffffffffa216160c <write_sysrq_trigger+60>: int3 0xffffffffa216160d <write_sysrq_trigger+61>: int3 0xffffffffa216160e <write_sysrq_trigger+62>: int3 0xffffffffa216160f <write_sysrq_trigger+63>: int3
Ubuntuでカーネルのソースコードを入手するには主に3種類の方法が存在します。
- Kernel Teamのgitリポジトリからリリースごとの最新のコードをcloneする
- 「
sudo apt install linux-source
」を実行する - 「
apt source linux-image-unsigned-$(uname -r)
」を実行する
開発版も含めて最新のソースコードの変更履歴が必要な場合は1を使います。リポジトリ名は
リポジトリからインストールできるカーネルパッケージの最新版で問題が起きているのであれば、
特定のカーネルパッケージのバージョンのソースコードを取得したいなら、
まずはソースパッケージリポジトリの有効化方法です。デスクトップ版なら/etc/
」
$ sudo sed -i 's/^# \(deb-src.*ubuntu.com.*\)$/\1/' /etc/apt/sources.list $ sudo apt update $ sudo apt dpkg-dev
最後のdpkg-devパッケージは、
$ mkdir -p ~/Packages/linux && cd $_ $ apt source linux-image-unsigned-$(uname -r) $ ls linux-5.11.0 linux_5.11.0-22.23.diff.gz linux_5.11.0-22.23.dsc linux_5.11.0.orig.tar.gz
今回は現在実行中のバージョンを指定するために$(uname -r)
」
crashは本来--src
」directory
」--src
」
crash> dis -s write_sysrq_trigger FILE: /build/linux-HvkI5B/linux-5.11.0/drivers/tty/sysrq.c LINE: 1151 dis: write_sysrq_trigger: source code is not available
コードが/build/
」
次のコマンドで上記のパスに合わせて、
$ mkdir -p ~/Packages/linux/build/linux-HvkI5B/ $ mv linux-5.11.0 ~/Packages/linux/build/linux-HvkI5B/
これでソースコードの準備は整いました。カーネルのソースコードディレクトリはcrashコマンド起動時に--src
」
$ crash --src ~/Packages/linux/ \ /usr/lib/debug/boot/vmlinux-5.11.0-22-generic /var/crash/202107040335/dump.202107040335 (略)
disコマンドに-s
」
crash> dis -s write_sysrq_trigger FILE: /build/linux-HvkI5B/linux-5.11.0/drivers/tty/sysrq.c LINE: 1151 1146 /* 1147 * writing 'C' to /proc/sysrq-trigger is like sysrq-C 1148 */ 1149 static ssize_t write_sysrq_trigger(struct file *file, const char __user *buf, 1150 size_t count, loff_t *ppos) * 1151 { 1152 if (count) { 1153 char c; 1154 1155 if (get_user(c, buf)) 1156 return -EFAULT; 1157 __handle_sysrq(c, false); 1158 } 1159 1160 return count; 1161 }
disコマンドの引数は、-s
」
クラッシュダンプの保存先をネットワーク上に変更する
前回はクラッシュダンプをローカルのファイルシステムに保存していました。しかしながらリモートで解析する予定がある、/etc/
」
設定方法自体は上記ファイルにコメントが記載されているため、/etc/
」
# SSH - username and hostname of the remote server that will receive the dump # and dmesg files. # SSH_KEY - Full path of the ssh private key to be used to login to the remote # server. use kdump-config propagate to send the public key to the # remote server #SSH="<user at server>" #SSH_KEY="<path>" SSH="shibata@192.168.0.59"
最低限必要な設定は、SSH
」SSH_
」/root/
」
設定ファイルの準備ができたら、kdump-config propagate
」
$ sudo kdump-config propagate Need to generate a new ssh key... The authenticity of host '192.168.0.59 (192.168.0.59)' can't be established. ECDSA key fingerprint is SHA256:2GCRtJY7/m5ZAk/m1LB1EYO88iUPHF1NJ3+QpgVURmw. Are you sure you want to continue connecting (yes/no/[fingerprint])? yes shibata@192.168.0.59's password: propagated ssh key /root/.ssh/kdump_id_rsa to server shibata@192.168.0.59
これだけで準備完了です。あとはシステムをクラッシュさせてみましょう。クラッシュしたマシンの/var/
」/var/
」
前述のソースパッケージのダウンロード先に保存するようにしておけば、
Ubuntu WikiのCrashdumpRecipeにはクラッシュダンプの解析に関する、
カーネルのクラッシュは致命的な問題につながることが多々あります。カーネルクラッシュに遭遇したら、