static bool test_strv_split_none(struct torture_context *tctx) { char *strv = NULL; int ret; /* NULL has 0 entries */ ret = strv_split(tctx, &strv, NULL, " "); torture_assert(tctx, ret == 0, "strv_split() on NULL failed"); torture_assert_int_equal(tctx, strv_count(strv), 0, "strv_split() on NULL failed"); TALLOC_FREE(strv); /* Empty string has 0 entries */ ret = strv_split(tctx, &strv, "", " "); torture_assert(tctx, ret == 0, "strv_split() on NULL failed"); torture_assert_int_equal(tctx, strv_count(strv), 0, "strv_split() on \"\" failed"); TALLOC_FREE(strv); /* String containing only separators has 0 entries */ ret = strv_split(tctx, &strv, "abcabcabc", "cba "); torture_assert(tctx, ret == 0, "strv_split() on NULL failed"); torture_assert_int_equal(tctx, strv_count(strv), 0, "strv_split() on seps-only failed"); TALLOC_FREE(strv); return true; }
static void test_strv_split(void) { _cleanup_strv_free_ char **l = NULL; const char str[] = "one,two,three"; l = strv_split(str, ","); assert_se(l); assert_se(strv_equal(l, (char**) input_table_multiple)); strv_free(l); l = strv_split(" one two\t three", WHITESPACE); assert_se(l); assert_se(strv_equal(l, (char**) input_table_multiple)); strv_free(l); /* Setting NULL for separator is equivalent to WHITESPACE */ l = strv_split(" one two\t three", NULL); assert_se(l); assert_se(strv_equal(l, (char**) input_table_multiple)); strv_free(l); l = strv_split_full(" one two\t three", NULL, 0); assert_se(l); assert_se(strv_equal(l, (char**) input_table_multiple)); strv_free(l); l = strv_split_full(" 'one' \" two\t three \" ' four five'", NULL, SPLIT_QUOTES); assert_se(l); assert_se(strv_equal(l, (char**) input_table_quoted)); strv_free(l); /* missing last quote ignores the last element. */ l = strv_split_full(" 'one' \" two\t three \" ' four five' ' ignored element ", NULL, SPLIT_QUOTES); assert_se(l); assert_se(strv_equal(l, (char**) input_table_quoted)); strv_free(l); /* missing last quote, but the last element is _not_ ignored with SPLIT_RELAX. */ l = strv_split_full(" 'one' \" two\t three \" ' four five", NULL, SPLIT_QUOTES | SPLIT_RELAX); assert_se(l); assert_se(strv_equal(l, (char**) input_table_quoted)); strv_free(l); /* missing separator between */ l = strv_split_full(" 'one' \" two\t three \"' four five'", NULL, SPLIT_QUOTES | SPLIT_RELAX); assert_se(l); assert_se(strv_equal(l, (char**) input_table_quoted)); strv_free(l); l = strv_split_full(" 'one' \" two\t three \"' four five", NULL, SPLIT_QUOTES | SPLIT_RELAX); assert_se(l); assert_se(strv_equal(l, (char**) input_table_quoted)); }
int xdg_user_dirs(char ***ret_config_dirs, char ***ret_data_dirs) { /* Implement the mechanisms defined in * * http://standards.freedesktop.org/basedir-spec/basedir-spec-0.6.html * * We look in both the config and the data dirs because we * want to encourage that distributors ship their unit files * as data, and allow overriding as configuration. */ const char *e; _cleanup_strv_free_ char **config_dirs = NULL, **data_dirs = NULL; e = getenv("XDG_CONFIG_DIRS"); if (e) { config_dirs = strv_split(e, ":"); if (!config_dirs) return -ENOMEM; } e = getenv("XDG_DATA_DIRS"); if (e) data_dirs = strv_split(e, ":"); else data_dirs = strv_new("/usr/local/share", "/usr/share", NULL); if (!data_dirs) return -ENOMEM; *ret_config_dirs = config_dirs; *ret_data_dirs = data_dirs; config_dirs = data_dirs = NULL; return 0; }
static int network_get_link_strv(const char *key, int ifindex, char ***ret) { _cleanup_free_ char *p = NULL, *s = NULL; _cleanup_strv_free_ char **a = NULL; int r; assert_return(ifindex > 0, -EINVAL); assert_return(ret, -EINVAL); if (asprintf(&p, "/run/systemd/netif/links/%d", ifindex) < 0) return -ENOMEM; r = parse_env_file(p, NEWLINE, key, &s, NULL); if (r == -ENOENT) return -ENODATA; if (r < 0) return r; if (isempty(s)) { *ret = NULL; return 0; } a = strv_split(s, " "); if (!a) return -ENOMEM; strv_uniq(a); r = strv_length(a); *ret = a; a = NULL; return r; }
static int network_get_strv(const char *key, char ***ret) { _cleanup_strv_free_ char **a = NULL; _cleanup_free_ char *s = NULL; int r; assert_return(ret, -EINVAL); r = parse_env_file("/run/systemd/netif/state", NEWLINE, key, &s, NULL); if (r == -ENOENT) return -ENODATA; if (r < 0) return r; if (isempty(s)) { *ret = NULL; return 0; } a = strv_split(s, " "); if (!a) return -ENOMEM; strv_uniq(a); r = strv_length(a); *ret = a; a = NULL; return r; }
static int network_link_get_strv(int ifindex, const char *key, char ***ret) { char path[STRLEN("/run/systemd/netif/links/") + DECIMAL_STR_MAX(ifindex) + 1]; _cleanup_strv_free_ char **a = NULL; _cleanup_free_ char *s = NULL; int r; assert_return(ifindex > 0, -EINVAL); assert_return(ret, -EINVAL); xsprintf(path, "/run/systemd/netif/links/%i", ifindex); r = parse_env_file(path, NEWLINE, key, &s, NULL); if (r == -ENOENT) return -ENODATA; if (r < 0) return r; if (isempty(s)) { *ret = NULL; return 0; } a = strv_split(s, " "); if (!a) return -ENOMEM; strv_uniq(a); r = strv_length(a); *ret = TAKE_PTR(a); return r; }
int parse_acl(const char *text, acl_t *acl_access, acl_t *acl_default, bool want_mask) { _cleanup_free_ char **a = NULL, **d = NULL; /* strings are not freed */ _cleanup_strv_free_ char **split; char **entry; int r = -EINVAL; _cleanup_(acl_freep) acl_t a_acl = NULL, d_acl = NULL; split = strv_split(text, ","); if (!split) return -ENOMEM; STRV_FOREACH(entry, split) { char *p; p = startswith(*entry, "default:"); if (!p) p = startswith(*entry, "d:"); if (p) r = strv_push(&d, p); else r = strv_push(&a, *entry); if (r < 0) return r; }
static int uid_get_array(uid_t uid, const char *variable, char ***array) { _cleanup_free_ char *p = NULL, *s = NULL; char **a; int r; assert(variable); r = file_of_uid(uid, &p); if (r < 0) return r; r = parse_env_file(p, NEWLINE, variable, &s, NULL); if (r == -ENOENT || (r >= 0 && isempty(s))) { if (array) *array = NULL; return 0; } if (r < 0) return r; a = strv_split(s, " "); if (!a) return -ENOMEM; strv_uniq(a); r = strv_length(a); if (array) *array = a; else strv_free(a); return r; }
static int add_modules(const char *p) { _cleanup_strv_free_ char **k = NULL; k = strv_split(p, ","); if (!k) return log_oom(); if (strv_extend_strv(&arg_proc_cmdline_modules, k, true) < 0) return log_oom(); return 0; }
static void test_strv_split(void) { char **s; unsigned i = 0; _cleanup_strv_free_ char **l = NULL; const char str[] = "one,two,three"; l = strv_split(str, ","); assert_se(l); STRV_FOREACH(s, l) { assert_se(streq(*s, input_table_multiple[i++])); }
static int dkr_pull_job_on_header(PullJob *j, const char *header, size_t sz) { _cleanup_free_ char *registry = NULL; char *token, *digest; DkrPull *i; int r; assert(j); assert(j->userdata); i = j->userdata; r = curl_header_strdup(header, sz, HEADER_TOKEN, &token); if (r < 0) return log_oom(); if (r > 0) { free(i->response_token); i->response_token = token; return 0; } r = curl_header_strdup(header, sz, HEADER_DIGEST, &digest); if (r < 0) return log_oom(); if (r > 0) { free(i->response_digest); i->response_digest = digest; return 0; } r = curl_header_strdup(header, sz, HEADER_REGISTRY, ®istry); if (r < 0) return log_oom(); if (r > 0) { char **l, **k; l = strv_split(registry, ","); if (!l) return log_oom(); STRV_FOREACH(k, l) { if (!hostname_is_valid(*k)) { log_error("Registry hostname is not valid."); strv_free(l); return -EBADMSG; } } strv_free(i->response_registries); i->response_registries = l; }
static int uid_get_array(uid_t uid, const char *variable, char ***array) { _cleanup_free_ char *p = NULL, *s = NULL; char **a; int r; if (asprintf(&p, "/run/systemd/users/%lu", (unsigned long) uid) < 0) return -ENOMEM; r = parse_env_file(p, NEWLINE, variable, &s, NULL); if (r < 0) { if (r == -ENOENT) { if (array) *array = NULL; return 0; } return r; } if (!s) { if (array) *array = NULL; return 0; } a = strv_split(s, " "); if (!a) return -ENOMEM; strv_uniq(a); r = strv_length(a); if (array) *array = a; else strv_free(a); return r; }
int path_split_and_make_absolute(const char *p, char ***ret) { char **l; int r; assert(p); assert(ret); l = strv_split(p, ":"); if (!l) return -ENOMEM; r = path_strv_make_absolute_cwd(l); if (r < 0) { strv_free(l); return r; } *ret = l; return r; }
static void test_strv_split_empty(void) { _cleanup_strv_free_ char **l = NULL; l = strv_split("", WHITESPACE); assert_se(l); assert_se(strv_isempty(l)); strv_free(l); l = strv_split("", NULL); assert_se(l); assert_se(strv_isempty(l)); strv_free(l); l = strv_split_full("", NULL, 0); assert_se(l); assert_se(strv_isempty(l)); strv_free(l); l = strv_split_full("", NULL, SPLIT_QUOTES); assert_se(l); assert_se(strv_isempty(l)); strv_free(l); l = strv_split_full("", WHITESPACE, SPLIT_QUOTES); assert_se(l); assert_se(strv_isempty(l)); strv_free(l); l = strv_split_full("", WHITESPACE, SPLIT_QUOTES | SPLIT_RELAX); assert_se(l); assert_se(strv_isempty(l)); strv_free(l); l = strv_split(" ", WHITESPACE); assert_se(l); assert_se(strv_isempty(l)); strv_free(l); l = strv_split(" ", NULL); assert_se(l); assert_se(strv_isempty(l)); strv_free(l); l = strv_split_full(" ", NULL, 0); assert_se(l); assert_se(strv_isempty(l)); strv_free(l); l = strv_split_full(" ", WHITESPACE, SPLIT_QUOTES); assert_se(l); assert_se(strv_isempty(l)); strv_free(l); l = strv_split_full(" ", NULL, SPLIT_QUOTES); assert_se(l); assert_se(strv_isempty(l)); strv_free(l); l = strv_split_full(" ", NULL, SPLIT_QUOTES | SPLIT_RELAX); assert_se(l); assert_se(strv_isempty(l)); }