diff --git a/meson.build b/meson.build
index 04214bff..352ac3b3 100644
--- meson.build
+++ meson.build
@@ -343,6 +343,15 @@ if enable_udisks2
   udisks2_dep = dependency('udisks2', version: '>= 1.97')
 endif
 
+# *** Check which command should be used to check processes blocking umount ***
+busy_processes_command = get_option('busy_processes_command')
+config_h.set_quoted('BUSY_PROCESS_COMMAND', busy_processes_command)
+if busy_processes_command == 'lsof'
+  config_h.set('BUSY_PROCESS_SPAWN', '"lsof -t \"%s\""')
+elif busy_processes_command == 'fuser'
+  config_h.set('BUSY_PROCESS_SPAWN', '"fuser -m \"%s\""')
+endif
+
 # *** Check for libsystemd-login ***
 enable_logind = get_option('logind')
 if enable_logind
@@ -500,6 +509,7 @@ gnome.post_install(
 )
 
 summary({
+  'busy_processes_command': busy_processes_command,
   'systemduserunitdir': systemd_systemduserunitdir,
   'tmpfilesdir': systemd_tmpfilesdir,
   'privileged_group': privileged_group,
diff --git a/meson_options.txt b/meson_options.txt
index c68fcf3c..60ca4935 100644
--- meson_options.txt
+++ meson_options.txt
@@ -1,3 +1,4 @@
+option('busy_processes_command', type: 'combo', choices: ['lsof', 'fuser'], value: 'lsof', description: 'Command used to detect processes blocking unmount')
 option('systemduserunitdir', type: 'string', value: '', description: 'custom directory for systemd user units, or \'no\' to disable')
 option('tmpfilesdir', type: 'string', value: '', description: 'custom directory for tmpfiles.d config files, or \'no\' to disable')
 option('privileged_group', type: 'string', value: 'wheel', description: 'custom name for group that has elevated permissions')
diff --git a/monitor/udisks2/gvfsudisks2mount.c b/monitor/udisks2/gvfsudisks2mount.c
index 466ecabc..f3781406 100644
--- monitor/udisks2/gvfsudisks2mount.c
+++ monitor/udisks2/gvfsudisks2mount.c
@@ -648,9 +648,9 @@ on_mount_op_reply (GMountOperation       *mount_operation,
 }
 
 static void
-lsof_command_cb (GObject       *source_object,
-                 GAsyncResult  *res,
-                 gpointer       user_data)
+busy_processes_command_cb (GObject       *source_object,
+                           GAsyncResult  *res,
+                           gpointer       user_data)
 {
   GTask *task = G_TASK (user_data);
   UnmountData *data = g_task_get_task_data (task);
@@ -671,15 +671,24 @@ lsof_command_cb (GObject       *source_object,
                                         NULL, /* gchar **out_standard_error */
                                         &error))
     {
-      g_printerr ("Error launching lsof(1): %s (%s, %d)\n",
-                  error->message, g_quark_to_string (error->domain), error->code);
+      g_warning ("Error launching %s(1): %s (%s, %d)\n",
+                 BUSY_PROCESS_COMMAND,
+                 error->message,
+                 g_quark_to_string (error->domain),
+                 error->code);
       g_error_free (error);
       goto out;
     }
 
-  if (!(WIFEXITED (exit_status) && WEXITSTATUS (exit_status) == 0))
+  if (!WIFEXITED (exit_status))
     {
-      g_printerr ("lsof(1) did not exit normally\n");
+      g_warning ("%s(1) killed by signal %d\n", BUSY_PROCESS_COMMAND, WTERMSIG (exit_status));
+      goto out;
+    }
+  if (WEXITSTATUS (exit_status) != 0)
+    {
+      /* A non-zero exit is expected when no processes are using the mount */
+      g_debug ("%s(1) exited with status %d\n", BUSY_PROCESS_COMMAND, WEXITSTATUS (exit_status));
       goto out;
     }
 
@@ -693,10 +702,16 @@ lsof_command_cb (GObject       *source_object,
         break;
 
       pid = strtol (p, &endp, 10);
-      if (pid == 0 && p == endp)
-        break;
+      if (p == endp)
+        {
+          /* strtol made no progress: skip one non-numeric character so the
+           * loop doesn't stall and subsequent PIDs are not lost. */
+          p++;
+          continue;
+        }
 
-      g_array_append_val (processes, pid);
+      if (pid != 0)
+        g_array_append_val (processes, pid);
 
       p = endp;
     }
@@ -711,9 +726,9 @@ lsof_command_cb (GObject       *source_object,
       is_stop = unmount_operation_is_stop (data->mount_operation);
 
       /* We want to emit the 'show-processes' signal even if launching
-       * lsof(1) failed or if it didn't return any PIDs. This is because
-       * it won't show e.g. root-owned processes operating on files
-       * on the mount point.
+       * lsof(1) or fuser(1) failed or if it didn't return any PIDs. This
+       * is because it won't show e.g. root-owned processes operating on
+       * files on the mount point.
        *
        * (unfortunately there's no way to convey that it failed)
        */
@@ -779,9 +794,9 @@ unmount_show_busy (GTask        *task,
   escaped_mount_point = g_strescape (mount_point, NULL);
   gvfs_udisks2_utils_spawn (10, /* timeout in seconds */
                             g_task_get_cancellable (task),
-                            lsof_command_cb,
+                            busy_processes_command_cb,
                             g_object_ref (task),
-                            "lsof -t \"%s\"",
+                            BUSY_PROCESS_SPAWN,
                             escaped_mount_point);
   g_free (escaped_mount_point);
 }
