2017年7月8日土曜日

systemd-nspawn を使って CentOS7 x86_64 の中に i686版 コンテナを作る

CentOS7 64bit版 を常用しているのですが、ちょっとだけ 32bit環境 に用がありまして、KVM ゲスト上で i686版 CentOS7 を使っていました。それでも良かったのですが、最近、systemd-nspawn でお手軽にコンテナが作れると知りましたので、備忘録です。

まず、KVM ゲスト上で出来るだけ最小の起動イメージを作ります。自分なりに試行錯誤して選定した結果が次です。
[root@cent7vm32 ~]# uname -a
Linux cent7vm32 3.10.0-514.26.2.el7.centos.plus.i686 #1 SMP Tue Jul 4 18:30:46 UTC 2017 i686 i686 i386 GNU/Linux
[root@cent7vm32 ~]# yum --releasever=7 --nogpg --installroot=/srv/mycon32 --disablerepo='*' --enablerepo=base \
install systemd passwd yum vim-minimal rootfiles initscripts dhclient net-tools iproute openssh-clients \
openssh-server NetworkManager bash-completion man
このイメージを tar などで固めて、ホスト環境へ転送します。あとは、起動するだけ。
[root@hoge srv]# uname -a
Linux hoge 3.10.0-514.26.2.el7.x86_64 #1 SMP Tue Jul 4 15:04:05 UTC 2017 x86_64 x86_64 x86_64 GNU/Linux
[root@hoge srv]# systemd-nspawn -D /var/lib/machines/mycon32 --personality=x86
Spawning container mycon32 on /var/lib/machines/mycon32.
Press ^] three times within 1s to kill container.
Failed to create directory /var/lib/machines/mycon32//sys/fs/selinux: No such file or directory
Failed to create directory /var/lib/machines/mycon32//sys/fs/selinux: No such file or directory
[root@mycon32 ~]# passwd
Changing password for user root.
New password: 
Retype new password: 
passwd: all authentication tokens updated successfully.
[root@mycon32 ~]# exit
logout
Container mycon32 exited successfully.
[root@hoge srv]# systemd-nspawn -b --network-bridge=virbr0 -D /var/lib/machines/mycon32 --personality=x86
Spawning container mycon32 on /var/lib/machines/mycon32.
Press ^] three times within 1s to kill container.
Failed to create directory /var/lib/machines/mycon32//sys/fs/selinux: No such file or directory
Failed to create directory /var/lib/machines/mycon32//sys/fs/selinux: No such file or directory
systemd 219 running in system mode. (+PAM +AUDIT +SELINUX +IMA -APPARMOR +SMACK +SYSVINIT +UTMP +LIBCRYPTSETUP +GCRYPT +GNUTLS +ACL +XZ -LZ4 -SECCOMP +BLKID +ELFUTILS +KMOD +IDN)
Detected virtualization systemd-nspawn.
Detected architecture x86.

Welcome to CentOS 7 (AltArch)!

Initializing machine ID from random generator.
Cannot add dependency job for unit display-manager.service, ignoring: Unit not found.
[  OK  ] Reached target Remote File Systems.
[  OK  ] Created slice Root Slice.
...
[  OK  ] Reached target Login Prompts.
[  OK  ] Started Cleanup of Temporary Directories.
[  OK  ] Started Login Service.

CentOS 7 (AltArch)
Kernel 3.10.0-514.26.2.el7.x86_64 on an i686

mycon32 login: root
Password: 
[root@mycon32 ~]# uname -a
Linux mycon32 3.10.0-514.26.2.el7.x86_64 #1 SMP Tue Jul 4 15:04:05 UTC 2017 i686 i686 i386 GNU/Linux
[root@mycon32 ~]# 
ネットワークは、virbr0 を割り当てましたので、コンテナ内の設定をします。インターフェースは host0 に見えます。
[root@mycon32 ~]# ifconfig host0
host0: flags=4098  mtu 1500
        ether 26:b3:01:6e:42:98  txqueuelen 1000  (Ethernet)
        RX packets 0  bytes 0 (0.0 B)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 0  bytes 0 (0.0 B)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

[root@mycon32 ~]# touch /etc/sysconfig/network
[root@mycon32 ~]# vi /etc/sysconfig/network-scripts/ifcfg-host0 
...
[root@mycon32 ~]# cat /etc/sysconfig/network-scripts/ifcfg-host0 
#
# network-scripts/ifcfg-host0
#
DEVICE=host0
ONBOOT=yes
BOOTPROTO=dhcp
USERCTL=no
NM_CONTROLLED=no
[root@mycon32 ~]# ifup host0

Determining IP information for host0... done.
[root@mycon32 ~]# ifconfig host0
host0: flags=4163  mtu 1500
        inet 192.168.122.25  netmask 255.255.255.0  broadcast 192.168.122.255
        inet6 fe80::24b3:1ff:fe6e:4298  prefixlen 64  scopeid 0x20
        ether 26:b3:01:6e:42:98  txqueuelen 1000  (Ethernet)
        RX packets 14  bytes 1251 (1.2 KiB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 12  bytes 1416 (1.3 KiB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

[root@mycon32 ~]# 
あとは、必要なものを入れ放題です。
[root@mycon32 ~]# yum check-update
Loaded plugins: fastestmirror
Loading mirror speeds from cached hostfile

audit-libs.i686                         2.6.5-3.el7_3.1                  updates
bash.i686                               4.2.46-21.el7_3                  updates
bind-libs-lite.i686                     32:9.9.4-38.el7_3.3              updates
bind-license.noarch                     32:9.9.4-38.el7_3.3              updates
ca-certificates.noarch                  2017.2.14-70.1.el7_3             updates
chkconfig.i686                          1.7.2-1.el7_3.1                  updates
device-mapper.i686                      7:1.02.135-1.el7_3.5             updates
device-mapper-libs.i686                 7:1.02.135-1.el7_3.5             updates
dracut.i686                             033-463.el7_3.2                  updates
expat.i686                              2.1.0-10.el7_3                   updates
gawk.i686                               4.0.2-4.el7_3.1                  updates
glibc.i686                              2.17-157.el7_3.4                 updates
glibc-common.i686                       2.17-157.el7_3.4                 updates
initscripts.i686                        9.49.37-1.el7_3.1                updates
kpartx.i686                             0.4.9-99.el7_3.3                 updates
krb5-libs.i686                          1.14.1-27.el7_3                  updates
libblkid.i686                           2.23.2-33.el7_3.2                updates
libgcrypt.i686                          1.5.3-13.el7_3.1                 updates
libmount.i686                           2.23.2-33.el7_3.2                updates
libnetfilter_conntrack.i686             1.0.6-1.el7_3                    updates
libsemanage.i686                        2.5-5.1.el7_3                    updates
libuuid.i686                            2.23.2-33.el7_3.2                updates
nspr.i686                               4.13.1-1.0.el7_3                 updates
nss.i686                                3.28.4-1.2.el7_3                 updates
nss-sysinit.i686                        3.28.4-1.2.el7_3                 updates
nss-tools.i686                          3.28.4-1.2.el7_3                 updates
nss-util.i686                           3.28.4-1.0.el7_3                 updates
openssh.i686                            6.6.1p1-35.el7_3                 updates
openssh-clients.i686                    6.6.1p1-35.el7_3                 updates
openssl-libs.i686                       1:1.0.1e-60.el7_3.1              updates
systemd.i686                            219-30.el7_3.9                   updates
systemd-libs.i686                       219-30.el7_3.9                   updates
tzdata.noarch                           2017b-1.el7                      updates
util-linux.i686                         2.23.2-33.el7_3.2                updates
vim-minimal.i686                        2:7.4.160-1.el7_3.1              updates
[root@mycon32 ~]# 
とても軽量(起動/停止が速い、KVM のようなオーバーヘッドが殆どない)で、非常に快適です。

2017-07-09追記、自動起動の設定方法
Arch Linux の wiki を参考にさせてもらいました。ありがたや!
https://wiki.archlinuxjp.org/index.php/Systemd-nspawn
[root@hoge ~]# systemctl enable machines.target
[root@hoge ~]# systemctl enable systemd-nspawn@mycon32.service
コンテナ mycon32 の起動パラメータをカスタマイズするには、次のようにします。
[root@hoge ~]# env SYSTEMD_EDITOR=vim systemctl edit systemd-nspawn@mycon32    ★これで vim が立ち上がります
...
[root@hoge ~]# cat /etc/systemd/system/systemd-nspawn@mycon32.service.d/override.conf
[Unit]
After=multi-user.target    ★ここがミソ(秘密の裏技?)です。これをしないと virbr0 の初期化より先にstartされ、起動に失敗します
                           ★network-online.target というのもあり、字面はそちらのほうが適切そうですが、うまく行きませんでした
[Service]
ExecStart=    ★バカバカしいですが、この行も必要なのです。なんでやねん
ExecStart=/usr/bin/systemd-nspawn --quiet --keep-unit --boot --link-journal=try-guest --network-bridge=virbr0 --machine=%I --personality=x86
再起動後の様子です。コンテナ内に sshd を立てておけば、ホスト側から ssh 接続できるので便利かと思います。
[root@hoge ~]# machinectl  
MACHINE CLASS     SERVICE
conf256 container nspawn    ちなみにこちらは、同様にして作成した fedora25 が入ったコンテナです
mycon32 container nspawn 

2 machines listed.
[root@hoge ~]# machinectl status mycon32
mycon32
           Since: Sun 2017-07-09 09:58:29 JST; 41min ago
          Leader: 5489 (systemd)
         Service: nspawn; class container
            Root: /var/lib/machines/mycon32
           Iface: virbr0
         Address: 192.168.122.25
                  fe80::24b3:1ff:fe6e:4298%5
              OS: CentOS 7 (AltArch)
            Unit: systemd-nspawn@mycon32.service
                  |-5471 /usr/bin/systemd-nspawn --quiet --keep-unit --boot --link-journal=try-guest --network-bridge=virbr0 --machine=mycon32 --personality=x86
                  |-5489 /usr/lib/systemd/systemd
                  `-system.slice
                    |-console-getty.service
                    | `-5721 /sbin/agetty --noclear --keep-baud console 115200 38400 9600 vt220
                    |-sshd.service
                    | `-5718 /usr/sbin/sshd -D
                    |-network.service
                    | `-6376 /sbin/dhclient -H mycon32 -1 -q -lf /var/lib/dhclient/dhclient--host0.lease -pf /var/run/dhclient-host0.pid host0
                    |-dbus.service
                    | `-5694 /bin/dbus-daemon --system --address=systemd: --nofork --nopidfile --systemd-activation
                    |-systemd-logind.service
                    | `-5687 /usr/lib/systemd/systemd-logind
                    `-systemd-journald.service
                      `-5599 /usr/lib/systemd/systemd-journald

Jul 09 09:58:30 hoge systemd-nspawn[5471]: Starting LSB: Bring up/down networking...
Jul 09 09:58:30 hoge systemd-nspawn[5471]: Starting OpenSSH server daemon...
Jul 09 09:58:30 hoge systemd-nspawn[5471]: [  OK  ] Started Permit User Sessions.
Jul 09 09:58:30 hoge systemd-nspawn[5471]: [  OK  ] Started Console Getty.
Jul 09 09:58:30 hoge systemd-nspawn[5471]: Starting Console Getty...
Jul 09 09:58:30 hoge systemd-nspawn[5471]: [  OK  ] Reached target Login Prompts.
Jul 09 09:58:30 hoge systemd-nspawn[5471]: [  OK  ] Started Login Service.
Jul 09 09:58:30 hoge systemd-nspawn[5471]: [  OK  ] Started OpenSSH server daemon.
Jul 09 09:58:36 hoge systemd-nspawn[5471]: CentOS 7 (AltArch)
Jul 09 09:58:36 hoge systemd-nspawn[5471]: Kernel 3.10.0-514.26.2.el7.x86_64 on an i686
[root@hoge ~]# ssh 192.168.122.25
root@192.168.122.25's password: 
Last login: Sun Jul  9 09:32:39 2017 from gateway
[root@mycon32 ~]# 
[root@mycon32 ~]# exit
logout
Connection to 192.168.122.25 closed.
[root@hoge ~]# lsbond -va    注.自作スクリプトです
DEVICE     IPADDR           HWADDR             PCI          i Link    Mode
================================================================================
team1      192.168.1.5      F0:DE:F1:xx:xx:xx  n/a          . ok  activebackup 
  |  link_watches: ethtool  delay_up=0  
* eth0     .                F0:DE:F1:xx:xx:xx  00:19.0      . ok  1000Mb/s Full

vb-conf256 n/a              FE:57:A1:33:89:1B  n/a          . ok 10000Mb/s Full
vb-mycon32 n/a              96:24:34:0B:FF:29  n/a          . ok 10000Mb/s Full
virbr0     192.168.122.1    52:54:00:BE:C2:87  n/a          . ok       n/a    .
virbr0-nic n/a              52:54:00:BE:C2:87  n/a          d x          -    -
wlan0      n/a              4E:0E:C7:xx:xx:xx  03:00.0      d x          -    -
[root@hoge ~]# brctl show
bridge name     bridge id               STP enabled     interfaces
virbr0          8000.525400bec287       yes             vb-conf256
                                                        vb-mycon32
                                                        virbr0-nic

2017-07-15追記、名前解決
/etc/nsswitch.conf に mymachines を追加すれば、コンテナ名で ssh できて便利になるようです。
[root@hoge ~]# grep mymachines /etc/nsswitch.conf
hosts:      files mdns4_minimal [NOTFOUND=return] dns myhostname mymachines
[root@hoge ~]# machinectl 
MACHINE CLASS     SERVICE
conf253 container nspawn 
conf256 container nspawn 
conf266 container nspawn 
mycon32 container nspawn 

4 machines listed.
[root@hoge ~]# ssh mycon32
root@mycon32's password: 
Last login: Tue Jul 11 20:43:01 2017 from gateway
[root@mycon32 ~]# 
人気ブログランキングへ にほんブログ村 IT技術ブログへ