Linuxの起動がものすごく遅い.5分ぐらい掛かる.原因を調査,解決したので手順をまとめておきます.
起動時のログを見る方法
systemdにはシステム起動時のログを分析する機能があります.使い方も簡単
まずは systemd-analyze を実行します
$ systemd-analyze
Startup finished in 16.337s (firmware) + 2.699s (loader) + 2.958s (kernel) + 5min 1.771s (userspace) = 5min 23.767s graphical.target reached after 5min 1.764s in userspace
起動には5分23秒かかっていて,そのうち userspace の処理で 5分1秒も掛かっていることが解ります.たしかに遅い.
より詳細なログを見ます.systemd-analyze に blame オプションを付けます.
$ systemd-analyze blame
以下のような表示がでました.
5min 400ms ifupdown-wait-online.service
12.723s ifupdown-pre.service
10.659s dev-sdc3.device
5.322s NetworkManager-wait-online.service
4.624s networking.service
2.605s udisks2.service
2.523s smartmontools.service
1.533s man-db.service
1.108s vmware.service
629ms logrotate.service
480ms apt-daily-upgrade.service
474ms apt-daily.service
243ms upower.service
200ms systemd-journal-flush.service
156ms vmware-USBArbitrator.service
120ms exim4.service
98ms user@1000.service
92ms nmbd.service
82ms accounts-daemon.service
71ms systemd-udev-trigger.service
65ms avahi-daemon.service
64ms smbd.service
62ms fancontrol.service
60ms NetworkManager.service
58ms polkit.service
54ms winbind.service
53ms systemd-logind.service
53ms apache2.service
52ms systemd-journald.service
49ms rtkit-daemon.service
49ms systemd-sysusers.service
47ms nvidia-persistenced.service
45ms keyboard-setup.service
45ms home.mount
44ms wpa_supplicant.service
43ms dictd.service
42ms phpsessionclean.service
39ms systemd-udevd.service
38ms ModemManager.service
36ms etc-setserial.service
34ms lm-sensors.service
34ms exim4-base.service
33ms setserial.service
33ms rng-tools-debian.service
以下省略問題があるのは先頭の1行
5min 400ms ifupdown-wait-online.service
この部分です. ifupdown-wait-online.service が猛烈に遅いようです.
サービスの詳細を調べる方法
ifupdown-wait-online.service とは一体何者でしょうか? 調べてみます
最初にサービスの稼働状況を確認します
$ systemctl status ifupdown-wait-online.service
結果
● ifupdown-wait-online.service - Wait for network to be configured by ifupdown
Loaded: loaded (/lib/systemd/system/ifupdown-wait-online.service; enabled; vendor preset: enabled)
Active: failed (Result: exit-code) since Sat 2021-07-31 16:27:14 JST; 24h ago
Process: 332 ExecStart=/lib/ifupdown/wait-online.sh (code=exited, status=1/FAILURE)
Main PID: 332 (code=exited, status=1/FAILURE)
CPU: 372msサービスはエラーで停止しています
サービスの定義ファイル /lib/systemd/system/ifupdown-wait-online.service の中身を眺めてみます
cat /lib/systemd/system/ifupdown-wait-online.service
[Unit] Description=Wait for network to be configured by ifupdown DefaultDependencies=no Before=network-online.target ConditionFileIsExecutable=/sbin/ifup [Service] Type=oneshot ExecStart=/lib/ifupdown/wait-online.sh RemainAfterExit=yes [Install] WantedBy=network-online.target
ExecStart=/lib/ifupdown/wait-online.sh ですから, 実体は /lib/ifupdown/wait-online.sh .拡張子的に sh のシェルスクリプトです
$ cat /lib/ifupdown/wait-online.sh
長いので,詳細は割愛.wait-online.shの冒頭は以下のように実装されています
#!/bin/sh set -e WAIT_ONLINE_METHOD="ifup" WAIT_ONLINE_IFACE="" WAIT_ONLINE_ADDRESS="" WAIT_ONLINE_TIMEOUT=300 [ -f /etc/default/networking ] && . /etc/default/networking
9行目で,設定ファイルは /etc/default/networking であることがわかります.
(4行目から7行目で,デフォルト値を設定./etc/default/networkingの内容で適宜値を変更する実装になっています)
/lib/ifupdown/wait-online.sh のデバッグ
デバッグするために,とりあえず -x オプションを指定してスクリプトを実行してみます
$ sudo /bin/sh -x /lib/ifupdown/wait-online.sh
結論だけ言うと,以下のコマンドで処理が止まっていました.
$ /sbin/ifquery --state eth1
原因
- /lib/ifupdown/wait-online.sh はネットワークインタフェースが利用可能になるまで wait するサービス
- このマシンでは eth0 と eth1 の2つのネットワークインタフェースが存在した
- しかし eth1 は使用していなかった(実験用の予備で普段はLANケーブルを外している)
- /lib/ifupdown/wait-online.sh は eth1がupするまで wait処理をおこない,時間切れで TIMEDOUTエラーで異常終了していた
ということでした
対処
eth1 の wait処理は不要なので /etc/default/networkingを編集して eth1は無視するように設定を変更しました.
WAIT_ONLINE_IFACE="eth0"
まとめ
関連するエントリ
同様の手順で別トラブルを解決したエントリもあります.併せてご覧ください!
pyopyopyo.hatenablog.com