]> granicus.if.org Git - zfs/commitdiff
Let zfs mount all tolerate in-progress mounts
authorDon Brady <don.brady@delphix.com>
Sat, 22 Jun 2019 23:41:21 +0000 (16:41 -0700)
committerBrian Behlendorf <behlendorf1@llnl.gov>
Sat, 22 Jun 2019 23:41:21 +0000 (16:41 -0700)
The zfs-mount service can unexpectedly fail to start when zfs
encounters a mount that is in progress. This service uses
zfs mount -a, which has a window between the time it checks if
the dataset was mounted and when the actual mount (via mount.zfs
binary) occurs.

The reason for the racing mounts is that both zfs-mount.target
and zfs-share.target are allowed to execute concurrently after
the import.  This is more of an issue with the relatively recent
addition of parallel mounting, and we should consider serializing
the mount and share targets.

Reviewed-by: Brian Behlendorf <behlendorf1@llnl.gov>
Reviewed by: John Kennedy <john.kennedy@delphix.com>
Reviewed-by: Allan Jude <allanjude@freebsd.org>
Signed-off-by: Don Brady <don.brady@delphix.com>
Closes #8881

cmd/zfs/zfs_main.c

index 9357bd2f38aa54ee714189937d3db8f72cd5078d..634303f809928cd034e24d350a02b74f9282837d 100644 (file)
@@ -6580,8 +6580,25 @@ share_mount_one(zfs_handle_t *zhp, int op, int flags, char *protocol,
                        return (1);
                }
 
-               if (zfs_mount(zhp, options, flags) != 0)
+               if (zfs_mount(zhp, options, flags) != 0) {
+                       /*
+                        * Check if a mount sneaked in after we checked
+                        */
+                       if (!explicit &&
+                           libzfs_errno(g_zfs) == EZFS_MOUNTFAILED) {
+                               usleep(10 * MILLISEC);
+                               libzfs_mnttab_cache(g_zfs, B_FALSE);
+
+                               if (zfs_is_mounted(zhp, NULL)) {
+                                       (void) fprintf(stderr, gettext(
+                                           "Ignoring previous 'already "
+                                           "mounted' error for '%s'\n"),
+                                           zfs_get_name(zhp));
+                                       return (0);
+                               }
+                       }
                        return (1);
+               }
                break;
        }