Skip to content

Commit

Permalink
Allow zfs unshare <protocol> -a
Browse files Browse the repository at this point in the history
Allow `zfs unshare <protocol> -a` command to share or unshare all datasets
of a given protocol, nfs or smb.

Additionally, enable most of ZFS Test Suite zfs_share/zfs_unshare test cases.
To work around some Illumos-specific functionalities ($SHARE/$UNSHARE) some
function wrappers were added around them.

Finally, fix and issue in smb_is_share_active() that would leave SMB shares
exported when invoking 'zfs unshare -a'

Reviewed-by: Giuseppe Di Natale <[email protected]>
Reviewed-by: Brian Behlendorf <[email protected]>
Signed-off-by: Turbo Fredriksson <[email protected]>
Signed-off-by: loli10K <[email protected]>
Closes openzfs#3238 
Closes openzfs#5367
  • Loading branch information
loli10K authored and behlendorf committed Nov 29, 2016
1 parent 251cb8d commit 2f71caf
Show file tree
Hide file tree
Showing 17 changed files with 287 additions and 46 deletions.
28 changes: 23 additions & 5 deletions cmd/zfs/zfs_main.c
Original file line number Diff line number Diff line change
Expand Up @@ -270,7 +270,7 @@ get_usage(zfs_help_t idx)
return (gettext("\tset <property=value> ... "
"<filesystem|volume|snapshot> ...\n"));
case HELP_SHARE:
return (gettext("\tshare <-a | filesystem>\n"));
return (gettext("\tshare <-a [nfs|smb] | filesystem>\n"));
case HELP_SNAPSHOT:
return (gettext("\tsnapshot|snap [-r] [-o property=value] ... "
"<filesystem|volume>@<snap> ...\n"));
Expand All @@ -279,7 +279,7 @@ get_usage(zfs_help_t idx)
"<-a | filesystem|mountpoint>\n"));
case HELP_UNSHARE:
return (gettext("\tunshare "
"<-a | filesystem|mountpoint>\n"));
"<-a [nfs|smb] | filesystem|mountpoint>\n"));
case HELP_ALLOW:
return (gettext("\tallow <filesystem|volume>\n"
"\tallow [-ldug] "
Expand Down Expand Up @@ -6436,14 +6436,19 @@ unshare_unmount(int op, int argc, char **argv)
char sharesmb[ZFS_MAXPROPLEN];

/* check options */
while ((c = getopt(argc, argv, op == OP_SHARE ? "a" : "af")) != -1) {
while ((c = getopt(argc, argv, op == OP_SHARE ? ":a" : "af")) != -1) {
switch (c) {
case 'a':
do_all = 1;
break;
case 'f':
flags = MS_FORCE;
break;
case ':':
(void) fprintf(stderr, gettext("missing argument for "
"'%c' option\n"), optopt);
usage(B_FALSE);
break;
case '?':
(void) fprintf(stderr, gettext("invalid option '%c'\n"),
optopt);
Expand Down Expand Up @@ -6475,6 +6480,19 @@ unshare_unmount(int op, int argc, char **argv)
unshare_unmount_node_t *node;
uu_avl_index_t idx;
uu_avl_walk_t *walk;
char *protocol = NULL;

if (op == OP_SHARE && argc > 0) {
if (strcmp(argv[0], "nfs") != 0 &&
strcmp(argv[0], "smb") != 0) {
(void) fprintf(stderr, gettext("share type "
"must be 'nfs' or 'smb'\n"));
usage(B_FALSE);
}
protocol = argv[0];
argc--;
argv++;
}

if (argc != 0) {
(void) fprintf(stderr, gettext("too many arguments\n"));
Expand Down Expand Up @@ -6567,8 +6585,8 @@ unshare_unmount(int op, int argc, char **argv)

switch (op) {
case OP_SHARE:
if (zfs_unshareall_bypath(node->un_zhp,
node->un_mountp) != 0)
if (zfs_unshareall_bytype(node->un_zhp,
node->un_mountp, protocol) != 0)
ret = 1;
break;

Expand Down
1 change: 1 addition & 0 deletions config/user-commands.m4
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,7 @@ AC_DEFUN([ZFS_AC_CONFIG_USER_COMMANDS_LINUX], [
AC_PATH_TOOL(READLINK, readlink, "")
AC_PATH_TOOL(SETFACL, setfacl, "")
AC_PATH_TOOL(SHARE, exportfs, "")
AC_PATH_TOOL(NET, net, "")
AC_PATH_TOOL(SWAP, swapon, "")
AC_PATH_TOOL(SWAPADD, swapon, "")
AC_PATH_TOOL(UDEVADM, udevadm, "")
Expand Down
1 change: 1 addition & 0 deletions include/libzfs.h
Original file line number Diff line number Diff line change
Expand Up @@ -763,6 +763,7 @@ extern int zfs_unshare_smb(zfs_handle_t *, const char *);
extern int zfs_unshareall_nfs(zfs_handle_t *);
extern int zfs_unshareall_smb(zfs_handle_t *);
extern int zfs_unshareall_bypath(zfs_handle_t *, const char *);
extern int zfs_unshareall_bytype(zfs_handle_t *, const char *, const char *);
extern int zfs_unshareall(zfs_handle_t *);
extern int zfs_deleg_share_nfs(libzfs_handle_t *, char *, char *, char *,
void *, void *, int, zfs_share_op_t);
Expand Down
8 changes: 5 additions & 3 deletions lib/libshare/smb.c
Original file line number Diff line number Diff line change
Expand Up @@ -354,17 +354,19 @@ smb_validate_shareopts(const char *shareopts)
static boolean_t
smb_is_share_active(sa_share_impl_t impl_share)
{
smb_share_t *iter = smb_shares;

if (!smb_available())
return (B_FALSE);

/* Retrieve the list of (possible) active shares */
smb_retrieve_shares();

while (smb_shares != NULL) {
if (strcmp(impl_share->sharepath, smb_shares->path) == 0)
while (iter != NULL) {
if (strcmp(impl_share->sharepath, iter->path) == 0)
return (B_TRUE);

smb_shares = smb_shares->next;
iter = iter->next;
}

return (B_FALSE);
Expand Down
14 changes: 14 additions & 0 deletions lib/libzfs/libzfs_mount.c
Original file line number Diff line number Diff line change
Expand Up @@ -988,6 +988,20 @@ zfs_unshareall_bypath(zfs_handle_t *zhp, const char *mountpoint)
return (zfs_unshare_proto(zhp, mountpoint, share_all_proto));
}

int
zfs_unshareall_bytype(zfs_handle_t *zhp, const char *mountpoint,
const char *proto)
{
if (proto == NULL)
return (zfs_unshare_proto(zhp, mountpoint, share_all_proto));
if (strcmp(proto, "nfs") == 0)
return (zfs_unshare_proto(zhp, mountpoint, nfs_only));
else if (strcmp(proto, "smb") == 0)
return (zfs_unshare_proto(zhp, mountpoint, smb_only));
else
return (1);
}

/*
* Remove the mountpoint associated with the current dataset, if necessary.
* We only remove the underlying directory if:
Expand Down
12 changes: 6 additions & 6 deletions man/man8/zfs.8
Original file line number Diff line number Diff line change
Expand Up @@ -160,12 +160,12 @@ zfs \- configures ZFS file systems

.LP
.nf
\fBzfs\fR \fBshare\fR \fB-a\fR | \fIfilesystem\fR
\fBzfs\fR \fBshare\fR [\fBnfs\fR|\fBsmb\fR] \fB-a\fR | \fIfilesystem\fR
.fi

.LP
.nf
\fBzfs\fR \fBunshare\fR \fB-a\fR \fIfilesystem\fR|\fImountpoint\fR
\fBzfs\fR \fBunshare\fR [\fBnfs\fR|\fBsmb\fR] \fB-a\fR | \fIfilesystem\fR|\fImountpoint\fR
.fi

.LP
Expand Down Expand Up @@ -2646,7 +2646,7 @@ Unmount the specified filesystem. The command can also be given a path to a \fBZ
.sp
.ne 2
.na
\fB\fBzfs share\fR \fB-a\fR | \fIfilesystem\fR\fR
\fB\fBzfs share\fR [\fBnfs\fR|\fBsmb\fR] \fB-a\fR | \fIfilesystem\fR\fR
.ad
.sp .6
.RS 4n
Expand All @@ -2658,7 +2658,7 @@ Shares available \fBZFS\fR file systems.
.ad
.sp .6
.RS 4n
Share all available \fBZFS\fR file systems. Invoked automatically as part of the boot process.
Share all available \fBZFS\fR file systems. Invoked automatically as part of the boot process. Additionally if one of \fBnfs\fR|\fBsmb\fR protocols is specified only share file systems whose \fBsharenfs\fR|\fBsharesmb\fR is set.
.RE

.sp
Expand All @@ -2676,11 +2676,11 @@ Share the specified filesystem according to the \fBsharenfs\fR and \fBsharesmb\f
.sp
.ne 2
.na
\fB\fBzfs unshare\fR \fB-a\fR | \fIfilesystem\fR|\fImountpoint\fR\fR
\fB\fBzfs unshare\fR [\fBnfs\fR|\fBsmb\fR] \fB-a\fR | \fIfilesystem\fR|\fImountpoint\fR\fR
.ad
.sp .6
.RS 4n
Unshares currently shared \fBZFS\fR file systems. This is invoked automatically as part of the shutdown process.
Unshares currently shared \fBZFS\fR file systems. This is invoked automatically as part of the shutdown process. Additionally if one of \fBnfs\fR|\fBsmb\fR is specified unshare only file systems currently shared by that protocol.
.sp
.ne 2
.na
Expand Down
19 changes: 11 additions & 8 deletions tests/runfiles/linux.run
Original file line number Diff line number Diff line change
Expand Up @@ -181,11 +181,12 @@ tests = ['cache_001_pos', 'cache_002_neg', 'canmount_001_pos',
'zfs_set_002_neg', 'zfs_set_003_neg', 'property_alias_001_pos']

# DISABLED: Tests need to be updated for Linux share behavior
#[tests/functional/cli_root/zfs_share]
#tests = ['zfs_share_001_pos', 'zfs_share_002_pos', 'zfs_share_003_pos',
# 'zfs_share_004_pos', 'zfs_share_005_pos', 'zfs_share_006_pos',
# 'zfs_share_007_neg', 'zfs_share_008_neg', 'zfs_share_009_neg',
# 'zfs_share_010_neg', 'zfs_share_011_pos']
# zfs_share_005_pos - needs investigation, probably unsupported NFS share format
[tests/functional/cli_root/zfs_share]
tests = ['zfs_share_001_pos', 'zfs_share_002_pos', 'zfs_share_003_pos',
'zfs_share_004_pos', 'zfs_share_006_pos',
'zfs_share_007_neg', 'zfs_share_008_neg', 'zfs_share_009_neg',
'zfs_share_010_neg', 'zfs_share_011_pos']

[tests/functional/cli_root/zfs_snapshot]
tests = ['zfs_snapshot_001_neg', 'zfs_snapshot_002_neg',
Expand All @@ -203,9 +204,11 @@ tests = ['zfs_unmount_001_pos', 'zfs_unmount_002_pos', 'zfs_unmount_003_pos',
'zfs_unmount_007_neg', 'zfs_unmount_008_neg']

# DISABLED: Tests need to be updated for Linux unshare behavior
#[tests/functional/cli_root/zfs_unshare]
#tests = ['zfs_unshare_001_pos', 'zfs_unshare_002_pos', 'zfs_unshare_003_pos',
# 'zfs_unshare_004_neg', 'zfs_unshare_005_neg']
# zfs_unshare_002_pos - zfs set sharenfs=off won't unshare if it was already off
# zfs_unshare_006_pos - some distros come with Samba "user shares" disabled
[tests/functional/cli_root/zfs_unshare]
tests = ['zfs_unshare_001_pos', 'zfs_unshare_003_pos',
'zfs_unshare_004_neg', 'zfs_unshare_005_neg']

[tests/functional/cli_root/zfs_upgrade]
tests = ['zfs_upgrade_001_pos', 'zfs_upgrade_002_pos', 'zfs_upgrade_003_pos',
Expand Down
1 change: 1 addition & 0 deletions tests/zfs-tests/include/commands.cfg.in
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,7 @@ export MOUNT="@MOUNT@"
export MPSTAT="@MPSTAT@"
export MV="@MV@"
export NAWK="@AWK@"
export NET="@NET@"
export NEWFS="@NEWFS@"
export NPROC="@NPROC@"
export PAGESIZE="@PAGESIZE@"
Expand Down
Loading

0 comments on commit 2f71caf

Please sign in to comment.