SONiCのイメージ更新
PCやスマートフォンのOSはたびたびアップデートが発生します。機能の追加だったり、バグの修正であったり、理由はさまざまです。Windowsのように小さな更新がたくさん適用されるものもあれば、iOSのように更新の際にイメージを書き換えてしまうものもあります。
SONiCはホワイトボックススイッチ用のOSで、現在も開発が進んでいるため、日々機能が追加されたりバグが修正されたりしています。安定しているとはいいがたい最新の機能を試してみたいような場合には、都度スイッチにインストールされているSONiCを最新に入れ替える必要があります。
SONiCのイメージ更新方法 - sonic_installer
SONiCのイメージを更新する方法はいくつかありますが、SONiCが動作している間に更新の準備を整え、再起動すれば新しいイメージで起動する、設定は新しいイメージに引き継がれる、という仕組みを実装しているのがsonic_installer
です。
sonic_installer install sonic-broadcom.bin
実行すると、確認を求められyes
と打ち込むとインストールが実行されます。動作中のイメージが上書きされるわけではなく、SONiCの起動イメージはストレージ上に2種類存在することになります。これをGRUBのデフォルト起動エントリー指定によって切り替える仕組みです。
sonic_installerの設定引継ぎ - config-setup
2020年2月現在、少なくともmasterブランチでは、以前のエントリで書いた/etc/ssh
引継ぎパッチを当てることができなくなっています。sonic_installer
周りのコードが大幅に書き換えられたからです。以前はsonic_installer
の中に直接cp
がべたっと書かれていたのですが、これが整理され、config-setup
スクリプトを呼び出すように変更されています。ZTP (Zero Touch Provisioning - 自動的に初期設定を完了させる仕組み) に対応させる際に必要だったようです。ちなみに、config-setup
はbash
スクリプトです。
config-setupの動作
使い方はパラメータなしで起動したときに表示されます。
Usage: config-setup < backup | boot | factory >
backup - Take a backup copy of SONiC configuration.
boot - Initialize/migrate SONiC configuration during system boot.
factory - Create factory default SONiC configuration and save it to
to /etc/sonic/config_db.json.
config-setup backup
を実行すれば(/host/old_config/
に)バックアップが作られ、config-setup boot
が実行されたときに(migration flagのファイルが存在していれば)バックアップから書き戻されるという動作になっています。
hook
/etc/ssh
を設定と同様にバックアップ、リストアしたいと考えたとき、まっさきに思いつくのはこのconfig-setup
スクリプトを(以前sonic_installer
に対してやったように)改造することでした。しかし、config-setup
の中身を読んでいくと、どうやらその改造をしなくて済むらしいことがわかってきました。backupとmigrationの処理の前後にhookが用意されているのです。つまり、スクリプトには手を加えず、hook処理のファイルを置いておけば、イメージ更新時にバックアップされ、更新したイメージの起動時にリストアされるようなのです。
config-setup
の中を調べると、run_hookdir
によってhookが実行されることがわかります。そして、run_hookdir
が呼び出されているのは3か所でした。
- 出荷時設定時の呼び出し (
generate_config
から呼ばれる) - バックアップ時の呼び出し (
do_config_backup
から呼ばれる) - リストア時の呼び出し (
do_config_migration
から呼ばれる)
config-setup hookを用意する
せっかくなので作成方法を調べつつ、以前パッチで仕込んでいた/etc/ssh
のバックアップとリストアをhookで実現してみます。
バックアップ
呼び出し自体は下記のようになっています。
run_hookdir ${CONFIG_PRE_MIGRATION_HOOKS} ${CONFIG_SETUP_PRE_MIGRATION_FLAG}
変数ですが、下記のように定義されています。
CONFIG_PRE_MIGRATION_HOOKS=/etc/config-setup/config-migration-pre-hooks.d
CONFIG_SETUP_PRE_MIGRATION_FLAG=${CONFIG_SETUP_VAR_DIR}/pending_pre_migration
ディレクトリの中に置かれているスクリプトを順次実行するようになっていますので、ディレクトリを掘って/etc/ssh
をバックアップするスクリプトを用意します。
#!/bin/sh
mkdir -p /host/old_ssh
cp -ar /etc/ssh/* /host/old_ssh/
. $script
で呼び出されるので実行権限をつける必要はないようです。つまり#!/bin/sh
も不要なのですが、ファイルを開いたときにシェルスクリプトと一目でわかるようにおまじないな感じで残しています。
リストア
バックアップと対応するようになっています。
呼び出し
run_hookdir ${CONFIG_POST_MIGRATION_HOOKS} ${CONFIG_SETUP_POST_MIGRATION_FLAG}
変数
CONFIG_POST_MIGRATION_HOOKS=/etc/config-setup/config-migration-post-hooks.d
CONFIG_SETUP_POST_MIGRATION_FLAG=${CONFIG_SETUP_VAR_DIR}/pending_post_migration
用意するスクリプトは下記です。
#!/bin/sh
cp -ar /host/old_ssh/* /etc/ssh/
rm -rf /host/old_ssh
動かしてみた
$ sudo sonic_installer install -y sonic-broadcom.bin
(中略)
Installed SONiC base image SONiC-OS successfully
Command: grub-set-default --boot-directory=/host 0
Command: config-setup backup
Taking backup of curent configuration
Command: sync;sync;sync
Command: sleep 3
Done
$ sudo shutdown -r now
$ Connection to XX.XXX.X.XXX closed by remote host.
Connection to XX.XXX.X.XXX closed.
host$ ssh admin@sonic
admin@XX.XXX.X.XXX's password:
hookは無事動いた!
のはいいのですが。更新後のディレクトリを眺めてみると問題が。
$ ls /etc/config-setup/
config-migration-post-hooks.d
preどこいった!?
preを保存するhookを用意する
たしかにリストア時の処理だけやればいいならこれでいいんですけど、うーん。
しかたがないのでpreのバックアップ・リストアもhookに仕込むことにします。本当はpostと同じように最終的に/etc/sonic/old_config/
に残るようにしておくのがいいんでしょうけど、そこは若干手抜きです。
バックアップ
#!/bin/sh
cp -ar /etc/config-setup/config-migration-pre-hooks.d /host/
リストア
#!/bin/sh
cp -ar /host/config-migration-pre-hooks.d /etc/config-setup/
rm -rf /host/config-migration-pre-hooks.d
無事リストアされて、めでたしめでたし。
おまけ: sonic_installerの新機能
$ sonic_installer
Usage: sonic_installer [OPTIONS] COMMAND [ARGS]...
SONiC image installation manager
Options:
--help Show this message and exit.
Commands:
binary_version Get version from local binary image file
cleanup Remove installed images which are not current...
install Install image from local binary or URL
list Print installed images
remove Uninstall image
rollback_docker Rollback docker image to previous version
set_default Choose image to boot from by default
set_next_boot Choose image for next reboot (one time...
upgrade_docker Upgrade docker image from local binary or URL
docker imageをいじくるコマンドが増えているようです。イメージを更新しても動作中のコンテナには影響ないはずですし、動作に反映させる際に整合性など考えるとおそらく再起動が必要でしょうから、現時点ではあまり使い道がないような感じもします。デバッグはやりやすくなるのかもしれません。