From: Ian Kent <raven@xxxxxxxxxx> Try and use the new fsinfo() system call when loading the mount table if possible. Signed-off-by: Ian Kent <raven@xxxxxxxxxx> --- src/core/mount.c | 6 ++++-- src/mount/mount-tool.c | 4 +++- src/shared/libmount-util.h | 28 ++++++++++++++++++++++++++++ src/shared/mount-util.c | 4 +++- src/shutdown/umount.c | 18 ++++++++++-------- 5 files changed, 48 insertions(+), 12 deletions(-) diff --git a/src/core/mount.c b/src/core/mount.c index 8b30a4db6a..299f2d56f6 100644 --- a/src/core/mount.c +++ b/src/core/mount.c @@ -1726,7 +1726,9 @@ static int mount_load_proc_self_mountinfo(Manager *m, bool set_flags) { assert(m); - r = libmount_parse(NULL, NULL, &table, &iter); + r = libmount_parse_fsinfo(&table, &iter); + if (r < 0) + r = libmount_parse(NULL, NULL, &table, &iter); if (r < 0) return log_error_errno(r, "Failed to parse /proc/self/mountinfo: %m"); @@ -1745,7 +1747,7 @@ static int mount_load_proc_self_mountinfo(Manager *m, bool set_flags) { options = mnt_fs_get_options(fs); fstype = mnt_fs_get_fstype(fs); - if (!device || !path) + if (!device || !path || !options || !fstype) continue; device_found_node(m, device, DEVICE_FOUND_MOUNT, DEVICE_FOUND_MOUNT); diff --git a/src/mount/mount-tool.c b/src/mount/mount-tool.c index 13f8a37ddf..2762060fb7 100644 --- a/src/mount/mount-tool.c +++ b/src/mount/mount-tool.c @@ -730,7 +730,9 @@ static int find_mount_points(const char *what, char ***list) { /* Returns all mount points obtained from /proc/self/mountinfo in *list, * and the number of mount points as return value. */ - r = libmount_parse(NULL, NULL, &table, &iter); + r = libmount_parse_fsinfo(&table, &iter); + if (r < 0) + r = libmount_parse(NULL, NULL, &table, &iter); if (r < 0) return log_error_errno(r, "Failed to parse /proc/self/mountinfo: %m"); diff --git a/src/shared/libmount-util.h b/src/shared/libmount-util.h index 7c3b855df5..e2d2383233 100644 --- a/src/shared/libmount-util.h +++ b/src/shared/libmount-util.h @@ -45,3 +45,31 @@ static inline int libmount_parse( *ret_iter = TAKE_PTR(iter); return 0; } + +static inline int libmount_parse_fsinfo( + struct libmnt_table **ret_table, + struct libmnt_iter **ret_iter) { + + _cleanup_(mnt_free_tablep) struct libmnt_table *table = NULL; + _cleanup_(mnt_free_iterp) struct libmnt_iter *iter = NULL; + int r; + + if (!mnt_has_fsinfo()) + return -ENOSYS; + + table = mnt_new_table(); + iter = mnt_new_iter(MNT_ITER_FORWARD); + if (!table || !iter) + return -ENOMEM; + + /* If source or path are specified, we use on the functions which ignore utab. + * Only if both are empty, we use mnt_table_parse_mtab(). */ + + r = mnt_table_parse_fsinfo(table); + if (r < 0) + return r; + + *ret_table = TAKE_PTR(table); + *ret_iter = TAKE_PTR(iter); + return 0; +} diff --git a/src/shared/mount-util.c b/src/shared/mount-util.c index 45fdd3b2da..ceb4a68999 100644 --- a/src/shared/mount-util.c +++ b/src/shared/mount-util.c @@ -37,7 +37,9 @@ int umount_recursive(const char *prefix, int flags) { again = false; - r = libmount_parse("/proc/self/mountinfo", NULL, &table, &iter); + r = libmount_parse_fsinfo(&table, &iter); + if (r < 0) + r = libmount_parse("/proc/self/mountinfo", NULL, &table, &iter); if (r < 0) return log_debug_errno(r, "Failed to parse /proc/self/mountinfo: %m"); diff --git a/src/shutdown/umount.c b/src/shutdown/umount.c index 8a5e80eeaa..7cf2987607 100644 --- a/src/shutdown/umount.c +++ b/src/shutdown/umount.c @@ -60,13 +60,15 @@ int mount_points_list_get(const char *mountinfo, MountPoint **head) { assert(head); - r = libmount_parse(mountinfo, NULL, &table, &iter); + r = libmount_parse_fsinfo(&table, &iter); + if (r < 0) + r = libmount_parse(mountinfo, NULL, &table, &iter); if (r < 0) return log_error_errno(r, "Failed to parse %s: %m", mountinfo ?: "/proc/self/mountinfo"); for (;;) { struct libmnt_fs *fs; - const char *path, *fstype; + const char *path, *fstype, *vfs_options, *fs_options; _cleanup_free_ char *options = NULL; unsigned long remount_flags = 0u; _cleanup_free_ char *remount_options = NULL; @@ -84,6 +86,10 @@ int mount_points_list_get(const char *mountinfo, MountPoint **head) { continue; fstype = mnt_fs_get_fstype(fs); + vfs_options = mnt_fs_get_vfs_options(fs); + fs_options = mnt_fs_get_fs_options(fs); + if (!fstype || !vfs_options || !fs_options) + continue; /* Combine the generic VFS options with the FS-specific * options. Duplicates are not a problem here, because the only @@ -93,13 +99,9 @@ int mount_points_list_get(const char *mountinfo, MountPoint **head) { * Even if there are duplicates later in mount_option_mangle() * they shouldn't hurt anyways as they override each other. */ - if (!strextend_with_separator(&options, ",", - mnt_fs_get_vfs_options(fs), - NULL)) + if (!strextend_with_separator(&options, ",", vfs_options, NULL)) return log_oom(); - if (!strextend_with_separator(&options, ",", - mnt_fs_get_fs_options(fs), - NULL)) + if (!strextend_with_separator(&options, ",", fs_options, NULL)) return log_oom(); /* Ignore mount points we can't unmount because they _______________________________________________ systemd-devel mailing list systemd-devel@xxxxxxxxxxxxxxxxxxxxx https://lists.freedesktop.org/mailman/listinfo/systemd-devel