diff options
-rw-r--r-- | include/pathnames.h | 3 | ||||
-rw-r--r-- | libmount/src/mountP.h | 2 | ||||
-rw-r--r-- | libmount/src/utils.c | 91 | ||||
-rw-r--r-- | tests/expected/libmount/utils-kernel-cmdline | 5 | ||||
-rw-r--r-- | tests/ts/libmount/files/kernel_cmdline | 1 | ||||
-rwxr-xr-x | tests/ts/libmount/utils | 9 |
6 files changed, 111 insertions, 0 deletions
diff --git a/include/pathnames.h b/include/pathnames.h index 58bba519a..a7f33fed5 100644 --- a/include/pathnames.h +++ b/include/pathnames.h @@ -152,5 +152,8 @@ /* wdctl path */ #define _PATH_WATCHDOG_DEV "/dev/watchdog" +/* kernel command line */ +#define _PATH_PROC_CMDLINE "/proc/cmdline" + #endif /* PATHNAMES_H */ diff --git a/libmount/src/mountP.h b/libmount/src/mountP.h index bbaa2c6c4..f28935d0d 100644 --- a/libmount/src/mountP.h +++ b/libmount/src/mountP.h @@ -147,6 +147,8 @@ extern const char *mnt_get_utab_path(void); extern int mnt_get_filesystems(char ***filesystems, const char *pattern); extern void mnt_free_filesystems(char **filesystems); +extern char *mnt_get_kernel_cmdline_option(const char *name); + /* tab.c */ extern int mnt_table_set_parser_fltrcb( struct libmnt_table *tb, int (*cb)(struct libmnt_fs *, void *), diff --git a/libmount/src/utils.c b/libmount/src/utils.c index 0cfefb347..624633dd8 100644 --- a/libmount/src/utils.c +++ b/libmount/src/utils.c @@ -881,6 +881,78 @@ char *mnt_get_fs_root(const char *path, const char *mnt) return res; } +/* + * Search for @name kernel command parametr. + * + * Returns newly allocated string with parameter argument if the @name is + * specified as "name=" or returns pointer to @name or returns NULL if not + * found. + * + * For example cmdline: "aaa bbb=BBB ccc" + * + * @name is "aaa" --returns--> "aaa" (pointer to @name) + * @name is "bbb=" --returns--> "BBB" (allocated) + * @name is "foo" --returns--> NULL + */ +char *mnt_get_kernel_cmdline_option(const char *name) +{ + FILE *f; + size_t len; + int val = 0; + char *p, *res = NULL; + char buf[BUFSIZ]; /* see kernel include/asm-generic/setup.h: COMMAND_LINE_SIZE */ + const char *path = _PATH_PROC_CMDLINE; + + assert(name); + assert(*name); + +#ifdef TEST_PROGRAM + path = safe_getenv("LIBMOUNT_KERNEL_CMDLINE"); + if (!path) + path = _PATH_PROC_CMDLINE; +#endif + f = fopen(path, "r"); + if (!f) + return NULL; + + p = fgets(buf, sizeof(buf), f); + fclose(f); + + if (!p || !*p || *p == '\n') + return NULL; + + len = strlen(buf); + *(buf + len - 1) = '\0'; /* remove last '\n' */ + + len = strlen(name); + if (len && *(name + len - 1) == '=') + val = 1; + + while (p && *p) { + if (p != buf) + p++; + if (!(p = strstr(p, name))) + break; /* not found the option */ + if (p != buf && !isblank(*(p - 1))) + continue; /* no space before the option */ + if (!val && *(p + len) != '\0' && !isblank(*(p + len))) + continue; /* no space behind the option */ + if (val) { + char *v = p + len; + + while (*p && !isblank(*p)) /* jump to the end of the argument */ + p++; + *p = '\0'; + res = strdup(v); + break; + } else + res = (char *) name; /* option without '=' */ + break; + } + + return res; +} + #ifdef TEST_PROGRAM int test_match_fstype(struct libmnt_test *ts, int argc, char *argv[]) { @@ -974,6 +1046,24 @@ int test_chdir(struct libmnt_test *ts, int argc, char *argv[]) return rc; } +int test_kernel_cmdline(struct libmnt_test *ts, int argc, char *argv[]) +{ + char *name = argv[1]; + char *res; + + res = mnt_get_kernel_cmdline_option(name); + if (!res) + printf("'%s' not found\n", name); + else if (res == name) + printf("'%s' found\n", name); + else { + printf("'%s' found, argument: '%s'\n", name, res); + free(res); + } + + return 0; +} + int main(int argc, char *argv[]) { @@ -986,6 +1076,7 @@ int main(int argc, char *argv[]) { "--mountpoint", test_mountpoint, "<path>" }, { "--fs-root", test_fsroot, "<path>" }, { "--cd-parent", test_chdir, "<path>" }, + { "--kernel-cmdline",test_kernel_cmdline, "<option> | <option>=" }, { NULL } }; diff --git a/tests/expected/libmount/utils-kernel-cmdline b/tests/expected/libmount/utils-kernel-cmdline new file mode 100644 index 000000000..2a6316583 --- /dev/null +++ b/tests/expected/libmount/utils-kernel-cmdline @@ -0,0 +1,5 @@ +'selinux=' found, argument: '0' +'selinux' not found +'ro' found +'ro=' not found +'root=' found, argument: 'UUID=33230ae2-1093-4353-824c-f7ca09a2a882' diff --git a/tests/ts/libmount/files/kernel_cmdline b/tests/ts/libmount/files/kernel_cmdline new file mode 100644 index 000000000..37a0c89e9 --- /dev/null +++ b/tests/ts/libmount/files/kernel_cmdline @@ -0,0 +1 @@ +rd.md=0 rd.lvm=0 rd.dm=0 KEYTABLE=us root=UUID=33230ae2-1093-4353-824c-f7ca09a2a882 rd.luks=0 SYSFONT=latarcyrheb-sun16 ro LANG=en_US.UTF-8 selinux=0 diff --git a/tests/ts/libmount/utils b/tests/ts/libmount/utils index d425400ad..6facaad10 100755 --- a/tests/ts/libmount/utils +++ b/tests/ts/libmount/utils @@ -76,4 +76,13 @@ ts_init_subtest "fs-root-subdir2" ts_valgrind $TESTPROG --fs-root /etc &> $TS_OUTPUT ts_finalize_subtest +ts_init_subtest "kernel-cmdline" +export LIBMOUNT_KERNEL_CMDLINE="$TS_SELF/files/kernel_cmdline" +ts_valgrind $TESTPROG --kernel-cmdline selinux= &>> $TS_OUTPUT +ts_valgrind $TESTPROG --kernel-cmdline selinux &>> $TS_OUTPUT +ts_valgrind $TESTPROG --kernel-cmdline ro &>> $TS_OUTPUT +ts_valgrind $TESTPROG --kernel-cmdline ro= &>> $TS_OUTPUT +ts_valgrind $TESTPROG --kernel-cmdline root= &>> $TS_OUTPUT +ts_finalize_subtest + ts_finalize |