In a standard multi-user setup, Guix and its daemon—the
guix-daemon
program—are installed by the system administrator.
Unprivileged users may use Guix tools to build packages or otherwise access
the store, and the daemon will do it on their behalf, ensuring that the
store is kept in a consistent state, and allowing built packages to be
shared among users.
There are currently two ways to set up and run the build daemon:
guix-daemon
as “root”, letting it run build processes as
unprivileged users taken from a pool of build users—this is the historical
approach;
guix-daemon
as a separate unprivileged user, relying on
Linux’s unprivileged user namespace functionality to set up isolated
environments—this is the option chosen when installing Guix on a
systemd-based distribution with the installation script (see 二进制文件安装).
The sections below describe each of these two configurations in more detail and summarize the kind of build isolation they provide.
When guix-daemon
runs as root
, you may not want package
build processes themselves to run as root
too, for obvious security
reasons. To avoid that, a special pool of build users should be
created for use by build processes started by the daemon. Having several
such users allows the daemon to launch distinct build processes under
separate UIDs, which guarantees that they do not interfere with each
other—an essential feature since builds are regarded as pure functions
(see 介绍).
在一个GNU/Linux系统上,可以这样创建一个构建用户池(用bash语法和shadow
命令):
# groupadd --system guixbuild # for i in $(seq -w 1 10); do useradd -g guixbuild -G guixbuild \ -d /var/empty -s $(which nologin) \ -c "Guix build user $i" --system \ guixbuilder$i; done
构建用户的数量决定了有多少个构建任务可以并行执行,即--max-jobs参数(see --max-jobs)。为了使用guix system
vm
和相关的命令,你需要把构建用户添加到kvm
用户组,以使它们访问/dev/kvm。为此,把-G
guixbuild
替换成-G guixbuild,kvm
(see 调用guix system
)。
The guix-daemon
program may then be run as root
with the
following command6:
# guix-daemon --build-users-group=guixbuild
In this setup, /gnu/store is owned by root
.
The second and preferred option is to run guix-daemon
as an
unprivileged user. It has the advantage of reducing the harm that can be
done should a build process manage to exploit a vulnerability in the
daemon. This option requires the use of Linux’s unprivileged user namespace
mechanism; today it is available and enabled by most GNU/Linux distributions
but can still be disabled. The installation script automatically determines
whether this option is available on your system (see 二进制文件安装).
When using this option, you only need to create one user account, and
guix-daemon
will run with the authority of that account:
# groupadd --system guix-daemon # useradd -g guix-daemon -G guix-daemon \ -d /var/empty -s $(which nologin) \ -c "Guix daemon privilege separation user" \ --system guix-daemon
In this configuration, /gnu/store is owned by the guix-daemon
user.
In both cases, the daemon starts build processes without privileges in an isolated or hermetic build environment—a “chroot”. On GNU/Linux, by default, the build environment contains nothing but:
/dev
独立的7,最小的/dev
文件夹;
/proc
文件夹;它只含有当前容器的进程,因为用了一个独立的进程PID命名空间;
localhost
映射到127.0.0.1
的条目;
The chroot does not contain a /home directory, and the HOME
environment variable is set to the non-existent /homeless-shelter.
This helps to highlight inappropriate uses of HOME
in the build
scripts of packages.
All this is usually enough to ensure details of the environment do not influence build processes. In some exceptional cases where more control is needed—typically over the date, kernel, or CPU—you can resort to a virtual build machine (see virtual build machines).
You can influence the directory where the daemon stores build trees via
the TMPDIR
environment variable. However, the build tree within the
chroot is always called /tmp/guix-build-name.drv-0, where
name is the derivation name—e.g., coreutils-8.24
. This way,
the value of TMPDIR
does not leak inside build environments, which
avoids discrepancies in cases where build processes capture the name of
their build tree.
The daemon also honors the http_proxy
and https_proxy
environment variables for HTTP and HTTPS downloads it performs, be it for
fixed-output derivations (see Derivations) or for substitutes
(see substitutes).
If your machine uses the systemd init system,
copying the prefix/lib/systemd/system/guix-daemon.service file
to /etc/systemd/system will ensure that guix-daemon
is
automatically started. Similarly, if your machine uses the Upstart init
system, copy the prefix/lib/upstart/system/guix-daemon.conf
file to /etc/init.
大致这样,因为虽然chroot环境里的/dev
包含的文件是固定的,大部分这些文件只有在主机有对应的文件时才能创建。