LXC非特権コンテナの設定方法に関するメモ(Arch Linux/Gentoo Linux)

背景

Arch Linuxでは、デフォルトでは非特権コンテナのサポートがなされておらず、一般ユーザーによるコンテナ実行は不可能な状況となっている。 公式ドキュメントとして高い信頼性・再現性を誇るArch Wikiには「非特権コンテナの設定方法」として、uid/gid mappingを伴う手順が示されているが、このドキュメント上での「非特権コンテナ」は「管理者権限で動作するLXCのinitプロセスがuid=0以外で動作するLXCコンテナ」を指しており、lxcそのものを一般ユーザーから実行できる手順とはなっていない。もとより、Arch開発陣は、非特権コンテナの実現に必要なカーネル名前空間のひとつである「ユーザー名前空間」の実装に対して批判的な見方(注)を示してきており、標準カーネルにはユーザー名前空間機能が組み込まれていない(CONFIG_USERNS=n)。これは/proc/.config.gzからも確認できる。

ここに示すのは、一般ユーザー権限で起動可能なLXCの非特権コンテナを、Archから利用するための、作業記録に過ぎない。筆者の手元ではGentooにおいても同様の手順(もしくはGentoo Wikiに記載の手順)で非特権コンテナが利用可能になることを確認済みだが、Arch, Gentooいずれについても異なるホスト環境下の再現性については厳密に検証を行っていない。また、Ubuntuを除くその他のディストリビューションについてはLXCそのものの動作について詳細な検証を行っていないため、ここでは立ち入らない。Ubuntuについては、デフォルトで非特権コンテナの利用が可能であるためこの記事では言及を避ける。

  • FS#36969 - [linux] 3.13 add CONFIG_USER_NS https://bugs.archlinux.org/task/36969 2017年8月、メインラインにuser.max_user_namespacesフラグが追加された影響もあり、若干の議論があった。後述のlinux-hardenedパッケージに関しても触れられている。

事前準備

  • まず、カスタムカーネルを作成する(注)。asp(1)を使うか, kernel.orgから直接カーネルソースコードを入手し、CONFIG_USERNS=yを設定してビルド、initramfsの生成・grub.cfgの更新を済ませておく。
  • ここでリブートし、カスタムカーネルからシステムを起動、ユーザー名前空間が有効化されていることを確認する。
$ zcat /proc/config.gz | grep USERNS
CONFIG_USERNS=y
  • LXCを公式パッケージからインストールする。また、仮想ネットワーク制御に便利なlibvirtも導入しておく+。
$ sudo pacman -Syy lxc libvirt
(以下略)
  • バイナリとして提供される別のカーネルパッケージにlinux-hardened(SELinux関連機能が有効化されたもの)がある。このカーネルはCONFIG_USERNS=yでコンパイルされているため、カーネルを自前でコンパイルしたくない場合はこのカーネルを用いることで非特権コンテナを利用できる。
  • Gentooにおいては、lxc, libvirtの導入時に USE flag の指定に注意が必要になる。カーネルでvirtioネットワークを含む準仮想化機構が有効化されていることを前提として、libvirt においては +virtio +dnsmasq, lxcにおいては +libvirt フラグを設定の上でemergeすることによってのみ動作を確認できた。

(とりあえずここまでUP)