如何防止 schroot 覆盖 chroot 系统上已存在的 passwd 文件和其他文件?

如何防止 schroot 覆盖 chroot 系统上已存在的 passwd 文件和其他文件?

当我必须修复 Debian 系统时,我尝试使用 schroot,因为不需要挂载绑定多个分区,非常方便。但是,与我的期望相反,schroot 决定覆盖我的 passwd 文件和其他配置文件(在/etc我的主目录中),这是我不喜欢的(有时会导致奇怪的消息)。有没有办法阻止这种行为?

我使用了 schroot 的类型directory,因为它似乎是我需要的类型。我检查了手册页,只找到了一个--preserve-environment选项,但从它的描述中我不确定它是否保留了 chroot 系统环境,或者只是将我的用户环境复制到 chroot 会话而不是干净的状态(这是默认设置)。

答案1

Schroot 做了很多事情来使 chroot 系统可用。这项工作是由脚本在/etc/schroot/setup.d/。这些操作由 schroot 的配置文件目录中的文件配置,由profileschroot 中的键指示根配置并默认为/etc/schroot/default/(schroot 配置还可以指定其他文件位置,详细信息请参阅手册)。启动动作包括:

  • fstab按照配置文件目录中的文件指示安装一些文件系统。
  • 将文件从主机系统复制到 chroot。要复制的文件列表是copyfiles从配置文件目录中的文件中读取的。
  • 覆盖 chroot 中的 NSS 数据库,从主机读取。要覆盖的数据库列表是nssdatabases从配置文件目录中的文件中读取的。这类似于复制文件,但它不仅仅复制/etc/passwd到 chroot,它还从其他源(例如 NIS 或 LDAP)检索条目。

默认情况下,copyfiles包含/etc/resolv.conf,以确保 chroot 中的程序能够像 chroot 之外的程序一样具有 DNS 访问权限。默认的 chroot 设置假设您希望 chroot 内部和外部的用户相同,因此nssdatabases包含所有常用的数据库,包括passwd,并且默认配置文件fstab不仅包含像/proc和 这样的文件系统,/dev这对许多程序的工作至关重要,而且还包含/home.

如果您不想覆盖 chroot 中的任何内容,请声明一个不带 和 的 schroot 配置文件copyfilesnssdatabases您可能希望有一个fstab可以挂载基本内容但不挂载 的配置文件/home

更有用的 schroot 配置将重现人类用户帐户及其主目录,但不会重现系统帐户。复制系统帐户是不幸的,因为 chroot 内部和外部可能存在不同的帐户。例如,Debian及其衍生版本的大多数系统软件都使用动态分配的帐户,因此大多数系统帐户的用户名和号码之间的对应关系取决于程序安装的顺序。为此,请从文件中删除passwdshadow和,group然后编写您自己的脚本,仅添加应复制的帐户。gshadownssdatabases

您可以编写以下脚本来/etc/schroot/setup.d/20appendaccounts仅复制真实用户范围内的帐户。

#!/bin/sh
## Append users and groups from the host.
set -e

. "$SETUP_DATA_DIR/common-data"
. "$SETUP_DATA_DIR/common-functions"
. "$SETUP_DATA_DIR/common-config"

if [ -z "$SETUP_NSSDATABASES" ] || ! [ -f "$SETUP_NSSDATABASES" ]; then
  exit 0
fi

DATABASES='group gshadow passwd shadow'

want () {
  grep -qx "#>>$1" "$SETUP_NSSDATABASES"
}

start () {
  sed -i -e '/^#begin added by schroot$/,/^#end added by schroot$/d' "$tmpfile"
  {
    echo '#begin added by schroot'
    getent "$db" | case $db in
      ## passwd, group: copy the range for local human accounts
      passwd) awk -F : "$FIRST_UID <= \$3 && \$3 <= $LAST_UID";;
      group) awk -F : "$FIRST_GID <= \$3 && \$3 <= $LAST_GID";;
      ## shadow, gshadow: copy only entries with a password hash
      shadow|gshadow) awk -F : '$2 ~ /^\$/';;
    esac
    echo '#end added by schroot'
  } >>"$tmpfile"
}

iterate () {
  for db in $DATABASES; do
    want "$db" || continue
    dbfile=$CHROOT_PATH/etc/$db
    tmpfile=$dbfile.$$
    [ -f "$dbfile" ] || continue
    cp -f -- "$dbfile" "$tmpfile"
    "$@"
    if ! [ -s "$tmpfile" ] || cmp -s -- "$dbfile" "$tmpfile"; then
      rm -f -- "$tmpfile"
    else
      mv -- "$tmpfile" "$dbfile"
    fi
  done
}

case $STAGE in
  setup-start|setup-recover)
    FIRST_UID=1000
    LAST_UID=29999
    FIRST_GID=1000
    LAST_GID=29999
    if [ -e /etc/adduser.conf ]; then . /etc/adduser.conf; fi
    umask 600
    iterate start;;
esac

编辑nssdatabases您的配置文件以包含以下行,或者放入setup.nssdatabases=default/nssdatabases-appendschroot 配置文件并将以下行写入default/nssdatabases.

#>>passwd
#>>shadow
#>>group
#>>gshadow
services
protocols
networks
hosts

Schroot 在其默认配置中不会覆盖主目录中的任何文件。--preserve-environment是关于环境变量的,与这里无关。

答案2

我创建了第二个配置文件,名为foo;您可以直接将这些添加到default配置文件中。配置文件是 的子目录/etc/schroot/,例如/etc/schroot/foo/, /etc/schroot/default/

diff -ruw default/fstab foo/fstab
--- default/fstab       2014-05-25 14:03:42.000000000 -0700
+++ foo/fstab   2014-04-03 16:36:42.644336952 -0700
@@ -7,7 +7,7 @@
 /sys            /sys            none    rw,bind         0       0
 /dev            /dev            none    rw,bind         0       0
 /dev/pts        /dev/pts        none    rw,bind         0       0
-/home           /home           none    rw,bind         0       0
+#/home           /home           none    rw,bind         0       0
 /tmp            /tmp            none    rw,bind         0       0

 # It may be desirable to have access to /run, especially if you wish
diff -ruw default/nssdatabases foo/nssdatabases
--- default/nssdatabases        2014-05-25 14:03:42.000000000 -0700
+++ foo/nssdatabases    2014-04-03 16:36:55.760398695 -0700
@@ -1,11 +1,11 @@
 # System databases to copy into the chroot from the host system.
 #
 # <database name>
-passwd
-shadow
-group
-gshadow
-services
-protocols
-networks
-hosts
+#passwd
+#shadow
+#group
+#gshadow
+#services
+#protocols
+#networks
+#hosts

/etc/default/copyfiles也存在,但我把它留在那里,因为你通常想要/etc/resolv.conf被复制。

相关内容