github.com/rawahars/moby@v24.0.4+incompatible/contrib/dockerd-rootless.sh (about)

     1  #!/bin/sh
     2  # dockerd-rootless.sh executes dockerd in rootless mode.
     3  #
     4  # Usage: dockerd-rootless.sh [DOCKERD_OPTIONS]
     5  #
     6  # External dependencies:
     7  # * newuidmap and newgidmap needs to be installed.
     8  # * /etc/subuid and /etc/subgid needs to be configured for the current user.
     9  # * Either one of slirp4netns (>= v0.4.0), VPNKit, lxc-user-nic needs to be installed.
    10  #
    11  # Recognized environment variables:
    12  # * DOCKERD_ROOTLESS_ROOTLESSKIT_NET=(slirp4netns|vpnkit|lxc-user-nic): the rootlesskit network driver. Defaults to "slirp4netns" if slirp4netns (>= v0.4.0) is installed. Otherwise defaults to "vpnkit".
    13  # * DOCKERD_ROOTLESS_ROOTLESSKIT_MTU=NUM: the MTU value for the rootlesskit network driver. Defaults to 65520 for slirp4netns, 1500 for other drivers.
    14  # * DOCKERD_ROOTLESS_ROOTLESSKIT_PORT_DRIVER=(builtin|slirp4netns): the rootlesskit port driver. Defaults to "builtin".
    15  # * DOCKERD_ROOTLESS_ROOTLESSKIT_SLIRP4NETNS_SANDBOX=(auto|true|false): whether to protect slirp4netns with a dedicated mount namespace. Defaults to "auto".
    16  # * DOCKERD_ROOTLESS_ROOTLESSKIT_SLIRP4NETNS_SECCOMP=(auto|true|false): whether to protect slirp4netns with seccomp. Defaults to "auto".
    17  #
    18  # See the documentation for the further information: https://docs.docker.com/go/rootless/
    19  
    20  set -e -x
    21  case "$1" in
    22  	"check" | "install" | "uninstall")
    23  		echo "Did you mean 'dockerd-rootless-setuptool.sh $@' ?"
    24  		exit 1
    25  		;;
    26  esac
    27  if ! [ -w "$XDG_RUNTIME_DIR" ]; then
    28  	echo "XDG_RUNTIME_DIR needs to be set and writable"
    29  	exit 1
    30  fi
    31  if ! [ -d "$HOME" ]; then
    32  	echo "HOME needs to be set and exist."
    33  	exit 1
    34  fi
    35  
    36  rootlesskit=""
    37  for f in docker-rootlesskit rootlesskit; do
    38  	if command -v $f > /dev/null 2>&1; then
    39  		rootlesskit=$f
    40  		break
    41  	fi
    42  done
    43  if [ -z "$rootlesskit" ]; then
    44  	echo "rootlesskit needs to be installed"
    45  	exit 1
    46  fi
    47  
    48  : "${DOCKERD_ROOTLESS_ROOTLESSKIT_NET:=}"
    49  : "${DOCKERD_ROOTLESS_ROOTLESSKIT_MTU:=}"
    50  : "${DOCKERD_ROOTLESS_ROOTLESSKIT_PORT_DRIVER:=builtin}"
    51  : "${DOCKERD_ROOTLESS_ROOTLESSKIT_SLIRP4NETNS_SANDBOX:=auto}"
    52  : "${DOCKERD_ROOTLESS_ROOTLESSKIT_SLIRP4NETNS_SECCOMP:=auto}"
    53  net=$DOCKERD_ROOTLESS_ROOTLESSKIT_NET
    54  mtu=$DOCKERD_ROOTLESS_ROOTLESSKIT_MTU
    55  if [ -z "$net" ]; then
    56  	if command -v slirp4netns > /dev/null 2>&1; then
    57  		# If --netns-type is present in --help, slirp4netns is >= v0.4.0.
    58  		if slirp4netns --help | grep -qw -- --netns-type; then
    59  			net=slirp4netns
    60  			if [ -z "$mtu" ]; then
    61  				mtu=65520
    62  			fi
    63  		else
    64  			echo "slirp4netns found but seems older than v0.4.0. Falling back to VPNKit."
    65  		fi
    66  	fi
    67  	if [ -z "$net" ]; then
    68  		if command -v vpnkit > /dev/null 2>&1; then
    69  			net=vpnkit
    70  		else
    71  			echo "Either slirp4netns (>= v0.4.0) or vpnkit needs to be installed"
    72  			exit 1
    73  		fi
    74  	fi
    75  fi
    76  if [ -z "$mtu" ]; then
    77  	mtu=1500
    78  fi
    79  
    80  dockerd="${DOCKERD:-dockerd}"
    81  
    82  if [ -z "$_DOCKERD_ROOTLESS_CHILD" ]; then
    83  	_DOCKERD_ROOTLESS_CHILD=1
    84  	export _DOCKERD_ROOTLESS_CHILD
    85  	if [ "$(id -u)" = "0" ]; then
    86  		echo "This script must be executed as a non-privileged user"
    87  		exit 1
    88  	fi
    89  	# `selinuxenabled` always returns false in RootlessKit child, so we execute `selinuxenabled` in the parent.
    90  	# https://github.com/rootless-containers/rootlesskit/issues/94
    91  	if command -v selinuxenabled > /dev/null 2>&1 && selinuxenabled; then
    92  		_DOCKERD_ROOTLESS_SELINUX=1
    93  		export _DOCKERD_ROOTLESS_SELINUX
    94  	fi
    95  	# Re-exec the script via RootlessKit, so as to create unprivileged {user,mount,network} namespaces.
    96  	#
    97  	# --copy-up allows removing/creating files in the directories by creating tmpfs and symlinks
    98  	# * /etc: copy-up is required so as to prevent `/etc/resolv.conf` in the
    99  	#         namespace from being unexpectedly unmounted when `/etc/resolv.conf` is recreated on the host
   100  	#         (by either systemd-networkd or NetworkManager)
   101  	# * /run: copy-up is required so that we can create /run/docker (hardcoded for plugins) in our namespace
   102  	exec $rootlesskit \
   103  		--net=$net --mtu=$mtu \
   104  		--slirp4netns-sandbox=$DOCKERD_ROOTLESS_ROOTLESSKIT_SLIRP4NETNS_SANDBOX \
   105  		--slirp4netns-seccomp=$DOCKERD_ROOTLESS_ROOTLESSKIT_SLIRP4NETNS_SECCOMP \
   106  		--disable-host-loopback --port-driver=$DOCKERD_ROOTLESS_ROOTLESSKIT_PORT_DRIVER \
   107  		--copy-up=/etc --copy-up=/run \
   108  		--propagation=rslave \
   109  		$DOCKERD_ROOTLESS_ROOTLESSKIT_FLAGS \
   110  		"$0" "$@"
   111  else
   112  	[ "$_DOCKERD_ROOTLESS_CHILD" = 1 ]
   113  	# remove the symlinks for the existing files in the parent namespace if any,
   114  	# so that we can create our own files in our mount namespace.
   115  	rm -f /run/docker /run/containerd /run/xtables.lock
   116  
   117  	if [ -n "$_DOCKERD_ROOTLESS_SELINUX" ]; then
   118  		# iptables requires /run in the child to be relabeled. The actual /run in the parent is unaffected.
   119  		# https://github.com/containers/podman/blob/e6fc34b71aa9d876b1218efe90e14f8b912b0603/libpod/networking_linux.go#L396-L401
   120  		# https://github.com/moby/moby/issues/41230
   121  		chcon system_u:object_r:iptables_var_run_t:s0 /run
   122  	fi
   123  
   124  	if [ "$(stat -c %T -f /etc)" = "tmpfs" ] && [ -L "/etc/ssl" ]; then
   125  		# Workaround for "x509: certificate signed by unknown authority" on openSUSE Tumbleweed.
   126  		# https://github.com/rootless-containers/rootlesskit/issues/225
   127  		realpath_etc_ssl=$(realpath /etc/ssl)
   128  		rm -f /etc/ssl
   129  		mkdir /etc/ssl
   130  		mount --rbind ${realpath_etc_ssl} /etc/ssl
   131  	fi
   132  
   133  	exec "$dockerd" "$@"
   134  fi