summaryrefslogtreecommitdiff
path: root/libmount
diff options
context:
space:
mode:
authorKarel Zak <kzak@redhat.com>2023-02-16 13:44:24 +0100
committerKarel Zak <kzak@redhat.com>2023-02-16 13:44:24 +0100
commit77bc38ced48a4e098e18546e456029731ea0588e (patch)
treec1c70d77fe18ed940452870fba295c089824518a /libmount
parente84f01c1a6ec76ccaac35a1cd253ff6f535626e5 (diff)
downloadutil-linux-77bc38ced48a4e098e18546e456029731ea0588e.tar.gz
libmount: add fsconfig() btrfs workaround
The new kernel mount API is not properly implemented in all FS drivers. See strace output: fsconfig(3, FSCONFIG_SET_STRING, "source", "/dev/sda", 0) = 0 fsconfig(3, FSCONFIG_SET_STRING, "context", "system_u:object_r:root_t:s0", 0) = 0 fsconfig(3, FSCONFIG_CMD_CREATE, NULL, NULL, 0) = -1 EINVAL (Invalid argument) Reported-by: Shinichiro Kawasaki <shinichiro.kawasaki@wdc.com> Signed-off-by: Karel Zak <kzak@redhat.com>
Diffstat (limited to 'libmount')
-rw-r--r--libmount/src/context.c2
-rw-r--r--libmount/src/context_mount.c3
-rw-r--r--libmount/src/hook_mount.c22
-rw-r--r--libmount/src/mountP.h1
4 files changed, 26 insertions, 2 deletions
diff --git a/libmount/src/context.c b/libmount/src/context.c
index 972853b3f..8db6b6950 100644
--- a/libmount/src/context.c
+++ b/libmount/src/context.c
@@ -165,6 +165,7 @@ int mnt_reset_context(struct libmnt_context *cxt)
cxt->mountdata = NULL;
cxt->flags = MNT_FL_DEFAULT;
cxt->noautofs = 1;
+ cxt->has_selinux_opt = 0;
cxt->map_linux = mnt_get_builtin_optmap(MNT_LINUX_MAP);
cxt->map_userspace = mnt_get_builtin_optmap(MNT_USERSPACE_MAP);
@@ -288,6 +289,7 @@ struct libmnt_context *mnt_copy_context(struct libmnt_context *o)
n->table_fltrcb_data = o->table_fltrcb_data;
n->noautofs = o->noautofs;
+ n->has_selinux_opt = o->has_selinux_opt;
return n;
failed:
diff --git a/libmount/src/context_mount.c b/libmount/src/context_mount.c
index d81741ea5..7491ec205 100644
--- a/libmount/src/context_mount.c
+++ b/libmount/src/context_mount.c
@@ -169,6 +169,9 @@ static int fix_optstr(struct libmnt_context *cxt)
rc = mnt_opt_set_quoted_value(opt, raw);
if (raw)
freecon(raw);
+
+ /* temporary for broken fsconfig() syscall */
+ cxt->has_selinux_opt = 1;
}
if (rc)
goto done;
diff --git a/libmount/src/hook_mount.c b/libmount/src/hook_mount.c
index 09a1f3f32..c60c3513b 100644
--- a/libmount/src/hook_mount.c
+++ b/libmount/src/hook_mount.c
@@ -120,7 +120,7 @@ static int configure_superblock(struct libmnt_context *cxt,
struct libmnt_opt *opt;
int rc;
- DBG(HOOK, ul_debugobj(hs, " configure FS"));
+ DBG(HOOK, ul_debugobj(hs, " config FS"));
ol = mnt_context_get_optlist(cxt);
if (!ol)
@@ -150,6 +150,7 @@ static int configure_superblock(struct libmnt_context *cxt,
return -errno;
}
+ DBG(HOOK, ul_debugobj(hs, " config done [rc=0]"));
return 0;
}
@@ -231,7 +232,7 @@ static int hook_create_mount(struct libmnt_context *cxt,
if (!src)
return -EINVAL;
- DBG(HOOK, ul_debugobj(hs, "create FS instance"));
+ DBG(HOOK, ul_debugobj(hs, "init FS"));
rc = fsconfig(api->fd_fs, FSCONFIG_SET_STRING, "source", src, 0);
set_syscall_status(cxt, "fsconfig", rc == 0);
@@ -239,6 +240,7 @@ static int hook_create_mount(struct libmnt_context *cxt,
if (!rc)
rc = configure_superblock(cxt, hs, api->fd_fs);
if (!rc) {
+ DBG(HOOK, ul_debugobj(hs, "create FS"));
rc = fsconfig(api->fd_fs, FSCONFIG_CMD_CREATE, NULL, NULL, 0);
set_syscall_status(cxt, "fsconfig", rc == 0);
}
@@ -551,6 +553,22 @@ static int hook_prepare(struct libmnt_context *cxt,
assert(cxt);
assert(hs == &hookset_mount);
+ /*
+ * The current kernel btrfs driver does not completely implement
+ * fsconfig() as it does not work with selinux stuff.
+ *
+ * Don't use the new mount API in this situation. Let's hope this issue
+ * is temporary.
+ */
+ {
+ const char *type = mnt_fs_get_fstype(cxt->fs);
+
+ if (type && strcmp(type, "btrfs") == 0 && cxt->has_selinux_opt) {
+ DBG(HOOK, ul_debugobj(hs, "don't use new API (btrfs issue)"));
+ return 0;
+ }
+ }
+
DBG(HOOK, ul_debugobj(hs, "prepare mount"));
ol = mnt_context_get_optlist(cxt);
diff --git a/libmount/src/mountP.h b/libmount/src/mountP.h
index 0d341c65a..80015f94c 100644
--- a/libmount/src/mountP.h
+++ b/libmount/src/mountP.h
@@ -427,6 +427,7 @@ struct libmnt_context
unsigned int enabled_textdomain : 1; /* bindtextdomain() called */
unsigned int noautofs : 1; /* ignore autofs mounts */
+ unsigned int has_selinux_opt : 1; /* temporary for broken fsconfig() syscall */
struct list_head hooksets_datas; /* global hooksets data */
struct list_head hooksets_hooks; /* global hooksets data */