みつきんのメモ

組み込みエンジニアです。Interface誌で「Yocto Projectではじめる 組み込みLinux開発入門」連載中

yocto master(20160323時点)でsystemd-networkdでエラー

先日、jethroでsystemd-networkdを有効化する方法を紹介したが、このままmasterに適用しても、systemd-networkdの起動に失敗する。

$ systemctl status systemd-networkd
* systemd-networkd.service - Network Service
   Loaded: loaded (/lib/systemd/system/systemd-networkd.service; enabled; vendor preset: enabled)
   Active: inactive (dead) (Result: exit-code) since Tue 2016-03-22 06:21:40 UTC; 2min 22s ago
     Docs: man:systemd-networkd.service(8)
  Process: 176 ExecStart=/lib/systemd/systemd-networkd (code=exited, status=1/FAILURE)
 Main PID: 176 (code=exited, status=1/FAILURE)
   Status: "Shutting down..."

Mar 22 06:21:40 raspberrypi3 systemd[1]: systemd-networkd.service: About to execute: /lib/systemd/systemd-networkd
Mar 22 06:21:40 raspberrypi3 systemd[1]: Starting Network Service...
Mar 22 06:21:40 raspberrypi3 systemd[1]: systemd-networkd.service: Main process exited, code=exited, status=1/FAILURE
Mar 22 06:21:40 raspberrypi3 systemd[1]: Failed to start Network Service.
Mar 22 06:21:40 raspberrypi3 systemd[1]: systemd-networkd.service: Unit entered failed state.
Mar 22 06:21:40 raspberrypi3 systemd[1]: systemd-networkd.service: Failed with result 'exit-code'.
Mar 22 06:21:40 raspberrypi3 systemd[1]: systemd-networkd.service: Service has no hold-off time, scheduling restart.
Mar 22 06:21:40 raspberrypi3 systemd[1]: Stopped Network Service.
Mar 22 06:21:40 raspberrypi3 systemd[1]: systemd-networkd.service: Start request repeated too quickly.
Mar 22 06:21:40 raspberrypi3 systemd[1]: Failed to start Network Service.

status=1/FAILUREとなっており、起動に失敗している事がわかる。 ifconfigしてみても、loしかいない。

$ ifconfig
lo        Link encap:Local Loopback  
          inet addr:127.0.0.1  Mask:255.0.0.0
          inet6 addr: ::1%1996203728/128 Scope:Host
          UP LOOPBACK RUNNING  MTU:65536  Metric:1
          RX packets:0 errors:0 dropped:0 overruns:0 frame:0
          TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:0 
          RX bytes:0 (0.0 B)  TX bytes:0 (0.0 B)

systemd-networkdをstartしてみる

試しにsystemd-networkdを手動で開始してみる。

$ systemctl start systemd-networkd.service
Job for systemd-networkd.service failed because the control process exited with error code.
See "systemctl status systemd-networkd.service" and "journalct -xe" for details.

詳細な情報を得るには、「systemctl status」や「journelctl -xe」を実行するようにアドバイスされるので、 journalctlを実行してみる。

$ journalctl -xe -u systemd-networkd.service
-- Logs begin at Tue 2016-03-22 06:21:34 UTC, end at Tue 2016-03-22 06:30:53 UTC. --
Mar 22 06:21:38 raspberrypi3 systemd[1]: systemd-networkd.service: Changed dead -> start
Mar 22 06:21:38 raspberrypi3 systemd[1]: systemd-networkd.service: Got notification message from PID 151 (STOPPING=1, STATUS=Shutting down...)
Mar 22 06:21:38 raspberrypi3 systemd[1]: systemd-networkd.service: Child 151 belongs to systemd-networkd.service
Mar 22 06:21:38 raspberrypi3 systemd[1]: systemd-networkd.service: Main process exited, code=exited, status=1/FAILURE
Mar 22 06:21:38 raspberrypi3 systemd[1]: systemd-networkd.service: Changed start -> failed
Mar 22 06:21:38 raspberrypi3 systemd[1]: systemd-networkd.service: Job systemd-networkd.service/start finished, result=failed
Mar 22 06:21:38 raspberrypi3 systemd[1]: Failed to start Network Service.
-- Subject: Unit systemd-networkd.service has failed
...(長いので省略)...

気になるログが見つかった。

Mar 22 06:28:07 raspberrypi3 systemd-networkd[199]: Cannot resolve user name systemd-network: No such process

systemdのソースを解析

まずは該当のログを出力している箇所を探す。

$ cd ~/rpi3/build_systemd/tmp/work/cortexa7hf-neon-vfpv4-poky-linux-gnueabi/systemd/1_229+gitAUTOINC+714c62b463-r0/git/src
$ grep -r 'Cannot resolve user name' .
./resolve/resolved.c:                log_error_errno(r, "Cannot resolve user name %s: %m", user);
./network/networkd-netdev-tuntap.c:                        return log_netdev_error_errno(netdev, r, "Cannot resolve user name %s: %m", t->user_name);
./network/networkd.c:                log_error_errno(r, "Cannot resolve user name %s: %m", user);
./timesync/timesyncd.c:                log_error_errno(r, "Cannot resolve user name %s: %m", user);

./network/networkd.cがそれっぽい。

~/rpi3/build_systemd/tmp/work/cortexa7hf-neon-vfpv4-poky-linux-gnueabi/systemd/1_229+gitAUTOINC+714c62b463-r0/git/src/network/networkd.c

int main(int argc, char *argv[]) {
...
        const char *user = "systemd-network";
...
        r = get_user_creds(&user, &uid, &gid, NULL, NULL);
        if (r < 0) {
                log_error_errno(r, "Cannot resolve user name %s: %m", user);
                goto out;
        }
...

systemd-networkというユーザーが見つからない場合は、エラー処理に回るようになっている様子。

ユーザーsystemd-networkを追加

試しに実行環境でsystemd-networkというユーザーを追加してみる。

$ useradd --system systemd-network

再起動後、ifconfigを実行。

$ ifconfig
eth0      Link encap:Ethernet  HWaddr B8:27:EB:BA:FD:E3  
          inet addr:192.168.21.99  Bcast:192.168.21.255  Mask:255.255.255.0
          inet6 addr: fe80::ba27:ebff:feba:fde3%1995753168/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          RX packets:77 errors:0 dropped:0 overruns:0 frame:0
          TX packets:41 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:1000 
          RX bytes:10266 (10.0 KiB)  TX bytes:6606 (6.4 KiB)

lo        Link encap:Local Loopback  
          inet addr:127.0.0.1  Mask:255.0.0.0
          inet6 addr: ::1%1995753168/128 Scope:Host
          UP LOOPBACK RUNNING  MTU:65536  Metric:1
          RX packets:0 errors:0 dropped:0 overruns:0 frame:0
          TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:0 
          RX bytes:0 (0.0 B)  TX bytes:0 (0.0 B)

eth0がwired.networkの設定になっている。

yoctoでの対処

手っ取り早くlocal.confで対処見てみる。

USERADD_PARAM_pn-systemd += "--system systemd-network"
PACKAGECONFIG_pn-systemd += " networkd"

別途、/etc/systemd/network/wired.networkは作成する必要があるが、これでsystemd-networkdが起動されるようになる。

masterブランチを使えるならばconnmanのほうが便利なので無理にsystemd-networkdを使う必要は無いだろう。