1#!/bin/ksh -p
2#
3# CDDL HEADER START
4#
5# The contents of this file are subject to the terms of the
6# Common Development and Distribution License (the "License").
7# You may not use this file except in compliance with the License.
8#
9# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10# or https://opensource.org/licenses/CDDL-1.0.
11# See the License for the specific language governing permissions
12# and limitations under the License.
13#
14# When distributing Covered Code, include this CDDL HEADER in each
15# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16# If applicable, add the following below this CDDL HEADER, with the
17# fields enclosed by brackets "[]" replaced with your own identifying
18# information: Portions Copyright [yyyy] [name of copyright owner]
19#
20# CDDL HEADER END
21#
22
23. $STF_SUITE/tests/functional/user_namespace/user_namespace_common.kshlib
24
25#
26# DESCRIPTION:
27#	Regression test for delegation of datasets to user namespaces.
28#
29# STRATEGY:
30#       1. Delegate a dataset to a user namespace.
31#	2. Check that 'zfs list' is only able to see inside the delegation.
32#	3. Check that 'zfs create' is able to create only inside the delegation.
33#	4. Check that the filesystems can be mounted inside the delegation,
34#	   and that file permissions are appropriate.
35#       5. Check that 'zfs destroy' is able to destroy only inside the delegation.
36#	6. Check that 'zfs unzone' has a desirable effect.
37#
38
39verify_runnable "both"
40
41user_ns_cleanup() {
42	if [ -n "$proc_ns_added" ]; then
43		log_must zfs unzone $proc_ns_added $TESTPOOL/userns
44	fi
45	if [ -n "$unshared_pid" ]; then
46		kill -9 $unshared_pid
47		# Give it a sec to make the global cleanup more reliable.
48		sleep 1
49	fi
50	log_must zfs destroy -r $TESTPOOL/userns
51}
52
53log_onexit user_ns_cleanup
54
55log_assert "Check zfs/zpool command delegation in user namespaces"
56
57# Create the baseline datasets.
58log_must zfs create -o zoned=on $TESTPOOL/userns
59log_must zfs create -o zoned=on $TESTPOOL/userns/testds
60# Partial match should be denied; hence we also set this to be 'zoned'.
61log_must zfs create -o zoned=on $TESTPOOL/user
62
63# 1. Create a user namespace with a cloned mount namespace, then delegate.
64unshare -Urm echo test
65if [ "$?" -ne "0" ]; then
66	log_unsupported "Failed to create user namespace"
67fi
68unshare -Urm /usr/bin/sleep 1h &
69unshared_pid=$!
70if [ "$?" -ne "0" ]; then
71	log_unsupported "Failed to create user namespace"
72fi
73proc_ns=/proc/$unshared_pid/ns/user
74sleep 2 # Wait for unshare to acquire user namespace
75log_note "unshare: child=${unshared_pid} proc_ns=${proc_ns}"
76
77NSENTER="nsenter -t $unshared_pid --all"
78
79$NSENTER echo test
80if [ "$?" -ne "0" ]; then
81	log_unsupported "Failed to enter user namespace"
82fi
83
84# 1b. Pre-test by checking that 'zone' does something new.
85list="$($NSENTER zfs list -r -H -o name | tr '\n' ' ')"
86log_must test -z "$list"
87log_must zfs zone $proc_ns $TESTPOOL/userns
88proc_ns_added="$proc_ns"
89
90# 2. 'zfs list'
91list="$($NSENTER zfs list -r -H -o name $TESTPOOL | tr '\n' ' ')"
92log_must test "$list" = "$TESTPOOL $TESTPOOL/userns $TESTPOOL/userns/testds "
93
94# 3. 'zfs create'
95log_must $NSENTER zfs create $TESTPOOL/userns/created
96log_mustnot $NSENTER zfs create $TESTPOOL/user/created
97
98# 4. Check file permissions (create mounts the filesystem).  The 'permissions'
99#    check is simply, does it get mapped to user namespace's root/root?
100log_must $NSENTER df -h /$TESTPOOL/userns/created
101log_must $NSENTER mkfile 8192 /$TESTPOOL/userns/created/testfile
102uidgid=$($NSENTER stat -c '%u %g' /$TESTPOOL/userns/created/testfile)
103log_must test "${uidgid}" = "0 0"
104
105# 5. 'zfs destroy'
106log_must $NSENTER zfs destroy $TESTPOOL/userns/created
107log_mustnot $NSENTER zfs destroy $TESTPOOL/user
108
109# 6. 'zfs unzone' should have an effect
110log_must zfs unzone $proc_ns $TESTPOOL/userns
111proc_ns_added=""
112list="$($NSENTER zfs list -r -H -o name | tr '\n' ' ')"
113log_must test -z "$list"
114
115log_pass "Check zfs/zpool command delegation in user namespaces"
116