From: Timo Sirainen Date: Wed, 10 May 2023 13:44:11 +0000 (+0300) Subject: lib-settings, config: Remove DEFLIST and DEFLIST_UNIQUE setting types X-Git-Tag: 2.4.0~2026 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=b1ce9207be6745dc200310f8e31cb0e7dded5e1d;p=thirdparty%2Fdovecot%2Fcore.git lib-settings, config: Remove DEFLIST and DEFLIST_UNIQUE setting types --- diff --git a/src/config/config-dump-full.c b/src/config/config-dump-full.c index ca97edeaa9..b68b79f7cc 100644 --- a/src/config/config-dump-full.c +++ b/src/config/config-dump-full.c @@ -245,8 +245,7 @@ config_dump_full_sections(struct config_parsed *config, struct ostream *output, enum config_dump_full_dest dest, unsigned int parser_idx, - const struct setting_parser_info *info, - unsigned int section_idx) + const struct setting_parser_info *info) { struct config_filter_parser *const *filters; struct config_export_context *export_ctx; @@ -286,8 +285,7 @@ config_dump_full_sections(struct config_parsed *config, i_assert(filter_info == info); const char *error; - ret = config_export_parser(export_ctx, parser_idx, - §ion_idx, &error); + ret = config_export_parser(export_ctx, parser_idx, &error); if (ret < 0) { ret = config_dump_full_handle_error(&dump_ctx, dest, start_offset, error); } else if (dest != CONFIG_DUMP_FULL_DEST_STDOUT && @@ -308,7 +306,6 @@ int config_dump_full(struct config_parsed *config, { struct config_export_context *export_ctx; const char *error; - unsigned int section_idx = 0; int fd = -1; struct dump_context dump_ctx = { @@ -403,8 +400,7 @@ int config_dump_full(struct config_parsed *config, o_stream_nsend(output, &blob_size, sizeof(blob_size)); o_stream_nsend(output, "", 1); /* no error */ } - if (config_export_parser(export_ctx, i, §ion_idx, - &error) < 0) { + if (config_export_parser(export_ctx, i, &error) < 0) { if (config_dump_full_handle_error(&dump_ctx, dest, blob_size_offset, error) < 0) break; @@ -416,7 +412,7 @@ int config_dump_full(struct config_parsed *config, int ret; T_BEGIN { ret = config_dump_full_sections(config, output, - dest, i, info, section_idx); + dest, i, info); } T_END; if (ret < 0) break; diff --git a/src/config/config-request.c b/src/config/config-request.c index 91d48b12a0..b04b5b971d 100644 --- a/src/config/config-request.c +++ b/src/config/config-request.c @@ -25,7 +25,6 @@ struct config_export_context { enum config_dump_flags flags; const struct config_module_parser *module_parsers; - unsigned int section_idx; }; static void config_export_size(string_t *str, uoff_t size) @@ -184,41 +183,14 @@ bool config_export_type(string_t *str, const void *value, return TRUE; } -static void -setting_export_section_name(string_t *str, const struct setting_define *def, - const void *set, unsigned int idx) -{ - const char *const *name; - size_t name_offset1; - - if (def->type != SET_DEFLIST_UNIQUE) { - /* not unique, use the index */ - str_printfa(str, "%u", idx); - return; - } - name_offset1 = def->list_info->type_offset1; - i_assert(name_offset1 != 0); - - name = CONST_PTR_OFFSET(set, name_offset1 - 1); - if (*name == NULL || **name == '\0') { - /* no name, this one isn't unique. use the index. */ - str_printfa(str, "%u", idx); - } else T_BEGIN { - str_append(str, settings_section_escape(*name)); - } T_END; -} - static void settings_export(struct config_export_context *ctx, const struct setting_parser_info *info, - bool parent_unique_deflist, const void *set, const void *change_set) { const struct setting_define *def; const void *value, *default_value, *change_value; - void *const *children, *const *change_children = NULL; - unsigned int i, count, count2; - size_t prefix_len; + unsigned int i, count; const char *str; char *key; bool dump, dump_default = FALSE; @@ -241,9 +213,6 @@ settings_export(struct config_export_context *ctx, /* hidden - dump default only if it's explicitly set */ /* fall through */ case CONFIG_DUMP_SCOPE_SET: - if (def->type == SET_DEFLIST || - def->type == SET_DEFLIST_UNIQUE) - break; if (*((const uint8_t *)change_value) < CONFIG_PARSER_CHANGE_EXPLICIT) { /* setting is unchanged in config file */ continue; @@ -251,9 +220,6 @@ settings_export(struct config_export_context *ctx, dump_default = TRUE; break; case CONFIG_DUMP_SCOPE_SET_AND_DEFAULT_OVERRIDES: - if (def->type == SET_DEFLIST || - def->type == SET_DEFLIST_UNIQUE) - break; if (*((const uint8_t *)change_value) < CONFIG_PARSER_CHANGE_INTERNAL) { /* setting is completely unchanged */ continue; @@ -270,7 +236,6 @@ settings_export(struct config_export_context *ctx, } dump = FALSE; - count = 0; children = NULL; str_truncate(ctx->value, 0); switch (def->type) { case SET_BOOL: @@ -288,25 +253,6 @@ settings_export(struct config_export_context *ctx, dump_default, &dump)) i_unreached(); break; - case SET_DEFLIST: - case SET_DEFLIST_UNIQUE: { - const ARRAY_TYPE(void_array) *val = value; - const ARRAY_TYPE(void_array) *change_val = change_value; - - if (!array_is_created(val)) - break; - - children = array_get(val, &count); - for (i = 0; i < count; i++) { - if (i > 0) - str_append_c(ctx->value, ' '); - setting_export_section_name(ctx->value, def, children[i], - ctx->section_idx + i); - } - change_children = array_get(change_val, &count2); - i_assert(count == count2); - break; - } case SET_STRLIST: { const ARRAY_TYPE(const_string) *val = value; const char *const *strings; @@ -337,7 +283,6 @@ settings_export(struct config_export_context *ctx, ctx->callback(str, strings[i+1], CONFIG_KEY_NORMAL, ctx->context); } - count = 0; break; } case SET_FILTER_ARRAY: { @@ -365,12 +310,7 @@ settings_export(struct config_export_context *ctx, if (hash_table_lookup(ctx->keys, key) == NULL) { enum config_key_type type; - if (def->offset + 1 == info->type_offset1 && - parent_unique_deflist) - type = CONFIG_KEY_UNIQUE_KEY; - else if (SETTING_TYPE_IS_DEFLIST(def->type)) - type = CONFIG_KEY_LIST; - else if (def->type == SET_FILTER_ARRAY) + if (def->type == SET_FILTER_ARRAY) type = CONFIG_KEY_FILTER_ARRAY; else type = CONFIG_KEY_NORMAL; @@ -380,23 +320,6 @@ settings_export(struct config_export_context *ctx, hash_table_insert(ctx->keys, key, key); } } - - i_assert(count == 0 || children != NULL); - prefix_len = str_len(ctx->prefix); - unsigned int section_start_idx = ctx->section_idx; - ctx->section_idx += count; - for (i = 0; i < count; i++) { - str_append(ctx->prefix, def->key); - str_append_c(ctx->prefix, SETTINGS_SEPARATOR); - setting_export_section_name(ctx->prefix, def, children[i], - section_start_idx + i); - str_append_c(ctx->prefix, SETTINGS_SEPARATOR); - settings_export(ctx, def->list_info, - def->type == SET_DEFLIST_UNIQUE, - children[i], change_children[i]); - - str_truncate(ctx->prefix, prefix_len); - } } } @@ -480,8 +403,7 @@ void config_export_free(struct config_export_context **_ctx) pool_unref(&ctx->pool); } -int config_export_all_parsers(struct config_export_context **_ctx, - unsigned int *section_idx) +int config_export_all_parsers(struct config_export_context **_ctx) { struct config_export_context *ctx = *_ctx; const char *error; @@ -491,7 +413,7 @@ int config_export_all_parsers(struct config_export_context **_ctx, *_ctx = NULL; for (i = 0; ctx->module_parsers[i].root != NULL; i++) { - if (config_export_parser(ctx, i, section_idx, &error) < 0) { + if (config_export_parser(ctx, i, &error) < 0) { i_error("%s", error); ret = -1; break; @@ -509,8 +431,7 @@ config_export_parser_get_info(struct config_export_context *ctx, } int config_export_parser(struct config_export_context *ctx, - unsigned int parser_idx, - unsigned int *section_idx, const char **error_r) + unsigned int parser_idx, const char **error_r) { const struct config_module_parser *module_parser = &ctx->module_parsers[parser_idx]; @@ -520,13 +441,10 @@ int config_export_parser(struct config_export_context *ctx, return -1; } - ctx->section_idx = *section_idx; T_BEGIN { void *set = settings_parser_get_set(module_parser->parser); - settings_export(ctx, module_parser->root, FALSE, set, + settings_export(ctx, module_parser->root, set, settings_parser_get_changes(module_parser->parser)); } T_END; - - *section_idx = ctx->section_idx; return 0; } diff --git a/src/config/config-request.h b/src/config/config-request.h index d3a3ba4f17..d0394bd162 100644 --- a/src/config/config-request.h +++ b/src/config/config-request.h @@ -27,7 +27,6 @@ enum config_dump_flags { enum config_key_type { CONFIG_KEY_NORMAL, CONFIG_KEY_LIST, - CONFIG_KEY_UNIQUE_KEY, CONFIG_KEY_FILTER_ARRAY, }; @@ -49,14 +48,12 @@ unsigned int config_export_get_parser_count(struct config_export_context *ctx); const char * config_export_get_import_environment(struct config_export_context *ctx); const char *config_export_get_base_dir(struct config_export_context *ctx); -int config_export_all_parsers(struct config_export_context **ctx, - unsigned int *section_idx); +int config_export_all_parsers(struct config_export_context **ctx); const struct setting_parser_info * config_export_parser_get_info(struct config_export_context *ctx, unsigned int parser_idx); int config_export_parser(struct config_export_context *ctx, - unsigned int parser_idx, - unsigned int *section_idx, const char **error_r); + unsigned int parser_idx, const char **error_r); void config_export_free(struct config_export_context **ctx); #endif diff --git a/src/config/doveconf.c b/src/config/doveconf.c index 6e5a4e0a74..72d34efce9 100644 --- a/src/config/doveconf.c +++ b/src/config/doveconf.c @@ -29,7 +29,6 @@ struct prefix_stack { unsigned int prefix_idx; - unsigned int str_pos; }; ARRAY_DEFINE_TYPE(prefix_stack, struct prefix_stack); @@ -43,7 +42,6 @@ struct config_dump_human_context { }; #define LIST_KEY_PREFIX "\001" -#define UNIQUE_KEY_SUFFIX "\xff" static struct config_parsed *config; static const char *indent_str = " !!!!"; @@ -64,7 +62,6 @@ config_request_get_strings(const char *key, const char *value, enum config_key_type type, void *context) { struct config_dump_human_context *ctx = context; - const char *p; switch (type) { case CONFIG_KEY_NORMAL: @@ -74,12 +71,6 @@ config_request_get_strings(const char *key, const char *value, value = p_strdup_printf(ctx->pool, LIST_KEY_PREFIX"%s=%s", key, value); break; - case CONFIG_KEY_UNIQUE_KEY: - p = strrchr(key, '/'); - i_assert(p != NULL); - value = p_strdup_printf(ctx->pool, "%.*s/"UNIQUE_KEY_SUFFIX"%s=%s", - (int)(p - key), key, p + 1, value); - break; case CONFIG_KEY_FILTER_ARRAY: return; } @@ -118,19 +109,10 @@ static struct prefix_stack prefix_stack_pop(ARRAY_TYPE(prefix_stack) *stack) } else { sc.prefix_idx = s[count-2].prefix_idx; } - sc.str_pos = s[count-1].str_pos; array_delete(stack, count-1, 1); return sc; } -static void prefix_stack_reset_str(ARRAY_TYPE(prefix_stack) *stack) -{ - struct prefix_stack *s; - - array_foreach_modifiable(stack, s) - s->str_pos = UINT_MAX; -} - static struct config_dump_human_context * config_dump_human_init(enum config_dump_scope scope) { @@ -323,20 +305,18 @@ config_dump_human_output(struct config_dump_human_context *ctx, ARRAY_TYPE(const_string) prefixes_arr; ARRAY_TYPE(prefix_stack) prefix_stack; struct prefix_stack prefix; - const char *const *strings, *const *args, *p, *str, *const *prefixes; + const char *const *strings, *p, *str, *const *prefixes; const char *key, *key2, *value; unsigned int i, j, count, prefix_count; unsigned int prefix_idx = UINT_MAX; size_t len, skip_len, setting_name_filter_len; size_t alt_setting_name_filter_len; - unsigned int section_idx = 0; - bool unique_key; setting_name_filter_len = setting_name_filter == NULL ? 0 : strlen(setting_name_filter); alt_setting_name_filter_len = alt_setting_name_filter == NULL ? 0 : strlen(alt_setting_name_filter); - if (config_export_all_parsers(&ctx->export_ctx, §ion_idx) < 0) + if (config_export_all_parsers(&ctx->export_ctx) < 0) i_unreached(); /* settings aren't checked - this can't happen */ array_sort(&ctx->strings, config_string_cmp); @@ -346,21 +326,11 @@ config_dump_human_output(struct config_dump_human_context *ctx, p_array_init(&prefixes_arr, ctx->pool, 32); for (i = 0; i < count && strings[i][0] == LIST_KEY_PREFIX[0]; i++) T_BEGIN { p = strchr(strings[i], '='); - i_assert(p != NULL); - if (p[1] == '\0') { - /* "strlist=" */ - str = p_strdup_printf(ctx->pool, "%s/", - t_strcut(strings[i]+1, '=')); - array_push_back(&prefixes_arr, &str); - } else { - /* string is in format: "list=0 1 2" */ - for (args = t_strsplit(p + 1, " "); *args != NULL; args++) { - str = p_strdup_printf(ctx->pool, "%s/%s/", - t_strcut(strings[i]+1, '='), - *args); - array_push_back(&prefixes_arr, &str); - } - } + i_assert(p != NULL && p[1] == '\0'); + /* "strlist=" */ + str = p_strdup_printf(ctx->pool, "%s/", + t_strcut(strings[i]+1, '=')); + array_push_back(&prefixes_arr, &str); } T_END; prefixes = array_get(&prefixes_arr, &prefix_count); @@ -370,15 +340,9 @@ config_dump_human_output(struct config_dump_human_context *ctx, i_assert(value != NULL); key = t_strdup_until(strings[i], value++); - unique_key = FALSE; bool hide_passwords = default_hide_passwords; p = strrchr(key, '/'); - if (p != NULL && p[1] == UNIQUE_KEY_SUFFIX[0]) { - key = t_strconcat(t_strdup_until(key, p + 1), - p + 2, NULL); - unique_key = TRUE; - } if (setting_name_filter_len > 0) { /* See if this setting matches the name filter. If we're asking for a full specific setting, @@ -410,9 +374,7 @@ config_dump_human_output(struct config_dump_human_context *ctx, if (strncmp(prefixes[prefix_idx], key, len) != 0) { prefix = prefix_stack_pop(&prefix_stack); indent--; - if (prefix.str_pos != UINT_MAX) - str_truncate(ctx->list_prefix, prefix.str_pos); - else if (!hide_key) { + if (!hide_key) { o_stream_nsend(output, indent_str, indent*2); o_stream_nsend_str(output, "}\n"); } @@ -429,8 +391,6 @@ config_dump_human_output(struct config_dump_human_context *ctx, if (strncmp(prefixes[j], key, len) == 0) { key2 = key + (prefix_idx == UINT_MAX ? 0 : strlen(prefixes[prefix_idx])); - prefix.str_pos = !unique_key ? UINT_MAX : - str_len(ctx->list_prefix); prefix_idx = j; prefix.prefix_idx = prefix_idx; array_push_back(&prefix_stack, &prefix); @@ -441,19 +401,10 @@ config_dump_human_output(struct config_dump_human_context *ctx, str_append_data(ctx->list_prefix, key2, p - key2); else str_append(ctx->list_prefix, key2); - if (unique_key && *value != '\0') { - if (strchr(value, ' ') == NULL) - str_printfa(ctx->list_prefix, " %s", value); - else - str_printfa(ctx->list_prefix, " \"%s\"", str_escape(value)); - } str_append(ctx->list_prefix, " {\n"); indent++; - if (unique_key) - goto end; - else - goto again; + goto again; } } if (!hide_key) { @@ -461,7 +412,6 @@ config_dump_human_output(struct config_dump_human_context *ctx, str_len(ctx->list_prefix)); } str_truncate(ctx->list_prefix, 0); - prefix_stack_reset_str(&prefix_stack); ctx->list_prefix_sent = TRUE; skip_len = prefix_idx == UINT_MAX ? 0 : strlen(prefixes[prefix_idx]); @@ -470,7 +420,6 @@ config_dump_human_output(struct config_dump_human_context *ctx, if (!hide_key) o_stream_nsend(output, indent_str, indent*2); key = strings[i] + skip_len; - if (unique_key) key++; const char *full_key = key; if (strip_prefix != NULL && str_begins(key, strip_prefix, &key)) key++; @@ -500,8 +449,6 @@ config_dump_human_output(struct config_dump_human_context *ctx, while (prefix_idx != UINT_MAX) { prefix = prefix_stack_pop(&prefix_stack); - if (prefix.str_pos != UINT_MAX) - break; prefix_idx = prefix.prefix_idx; indent--; if (!hide_key) { diff --git a/src/config/settings-get.pl b/src/config/settings-get.pl index 5f72da608d..d1c90c12b6 100755 --- a/src/config/settings-get.pl +++ b/src/config/settings-get.pl @@ -104,27 +104,8 @@ foreach my $file (@ARGV) { $code .= $_; $state = 0 if (/\/\* <\/settings checks> \*\//); } - - if ($state == 1 || $state == 3) { - if ($state == 1 && $cur_name ne "") { - if (/\.parent = /) { - delete($parsers{$cur_name}); - } - if (/DEFLIST.*".*",(.*)$/) { - my $value = $1; - if ($value =~ /.*&(.*)\)/) { - $parsers{$1} = 0; - $externs .= "extern const struct setting_parser_info $1;\n"; - } else { - $state = 3; - } - } - } elsif ($state == 3) { - if (/.*&(.*)\)/) { - $parsers{$1} = 0; - } - } - + + if ($state == 1) { s/^static const (struct master_settings master_default_settings)/$1/; $write = 1; @@ -173,9 +154,6 @@ print "};\n"; print "const struct setting_parser_info *all_default_roots[] = {\n"; foreach my $name (sort(keys %parsers)) { - my $module = $parsers{$name}; - next if (!$module); - print "\t&".$name.", \n"; } print "\tNULL\n"; diff --git a/src/config/test-config-parser.c b/src/config/test-config-parser.c index 954e02ade6..02a82daa2d 100644 --- a/src/config/test-config-parser.c +++ b/src/config/test-config-parser.c @@ -66,7 +66,6 @@ const struct setting_parser_info test_settings_root = { .defaults = &test_settings_defaults, .struct_size = sizeof(struct test_settings), - .parent = NULL, }; static const struct setting_parser_info *const roots[] = { diff --git a/src/lib-settings/settings-parser.c b/src/lib-settings/settings-parser.c index 1965f8b988..9aded32e5b 100644 --- a/src/lib-settings/settings-parser.c +++ b/src/lib-settings/settings-parser.c @@ -27,7 +27,6 @@ struct setting_link { const char *full_key; /* Points to array inside parent->set_struct. - SET_DEFLIST : array of set_structs SET_STRLIST : array of const_strings */ ARRAY_TYPE(void_array) *array; /* Pointer to structure containing the values */ @@ -35,8 +34,6 @@ struct setting_link { /* Pointer to structure containing non-zero values for settings that have been changed. */ void *change_struct; - /* SET_DEFLIST: array of change_structs */ - ARRAY_TYPE(void_array) *change_array; }; struct setting_parser_context { @@ -65,79 +62,6 @@ static const struct setting_parser_info strlist_info = { HASH_TABLE_DEFINE_TYPE(setting_link, struct setting_link *, struct setting_link *); -static void -setting_parser_copy_defaults(struct setting_parser_context *ctx, - const struct setting_parser_info *info, - struct setting_link *link); -static int -settings_apply(struct setting_link *dest_link, - const struct setting_link *src_link, - pool_t pool, const char **conflict_key_r); - -static void -copy_unique_defaults(struct setting_parser_context *ctx, - const struct setting_define *def, - struct setting_link *link) -{ - ARRAY_TYPE(void_array) *arr = - STRUCT_MEMBER_P(link->set_struct, def->offset); - ARRAY_TYPE(void_array) *carr = NULL; - struct setting_link *new_link; - struct setting_parser_info info; - const char *const *keyp, *key, *prefix; - void *const *children; - void *new_set, *new_changes = NULL; - char *full_key; - unsigned int i, count; - - if (!array_is_created(arr)) - return; - - children = array_get(arr, &count); - if (link->change_struct != NULL) { - carr = STRUCT_MEMBER_P(link->change_struct, def->offset); - i_assert(!array_is_created(carr)); - p_array_init(carr, ctx->set_pool, count + 4); - } - p_array_init(arr, ctx->set_pool, count + 4); - - i_zero(&info); - info = *def->list_info; - - for (i = 0; i < count; i++) T_BEGIN { - new_set = p_malloc(ctx->set_pool, info.struct_size); - array_push_back(arr, &new_set); - - if (link->change_struct != NULL) { - i_assert(carr != NULL); - new_changes = p_malloc(ctx->set_pool, info.struct_size); - array_push_back(carr, &new_changes); - } - - keyp = CONST_PTR_OFFSET(children[i], info.type_offset1-1); - key = settings_section_escape(*keyp); - - new_link = p_new(ctx->set_pool, struct setting_link, 1); - prefix = link->full_key == NULL ? - t_strconcat(def->key, SETTINGS_SEPARATOR_S, NULL) : - t_strconcat(link->full_key, SETTINGS_SEPARATOR_S, - def->key, SETTINGS_SEPARATOR_S,NULL); - full_key = p_strconcat(ctx->set_pool, prefix, key, NULL); - new_link->full_key = full_key; - new_link->parent = link; - new_link->info = def->list_info; - new_link->array = arr; - new_link->change_array = carr; - new_link->set_struct = new_set; - new_link->change_struct = new_changes; - i_assert(hash_table_lookup(ctx->links, full_key) == NULL); - hash_table_insert(ctx->links, full_key, new_link); - - info.defaults = children[i]; - setting_parser_copy_defaults(ctx, &info, new_link); - } T_END; -} - static void setting_parser_copy_defaults(struct setting_parser_context *ctx, const struct setting_parser_info *info, @@ -171,9 +95,6 @@ setting_parser_copy_defaults(struct setting_parser_context *ctx, } break; } - case SET_DEFLIST_UNIQUE: - copy_unique_defaults(ctx, def, link); - break; default: break; } @@ -360,32 +281,8 @@ static int get_enum(struct setting_parser_context *ctx, const char *value, return 0; } -static void -setting_link_init_set_struct(struct setting_parser_context *ctx, - struct setting_link *link) -{ - void *ptr; - - link->set_struct = p_malloc(ctx->set_pool, link->info->struct_size); - if ((ctx->flags & SETTINGS_PARSER_FLAG_TRACK_CHANGES) != 0) { - link->change_struct = - p_malloc(ctx->set_pool, link->info->struct_size); - array_push_back(link->change_array, &link->change_struct); - } - - setting_parser_copy_defaults(ctx, link->info, link); - array_push_back(link->array, &link->set_struct); - - if (link->info->parent_offset1 != 0 && link->parent != NULL) { - ptr = STRUCT_MEMBER_P(link->set_struct, - link->info->parent_offset1-1); - *((void **)ptr) = link->parent->set_struct; - } -} - static int ATTR_NULL(2) setting_link_add(struct setting_parser_context *ctx, - const struct setting_define *def, const struct setting_link *link_copy, char *key) { struct setting_link *link; @@ -393,8 +290,7 @@ setting_link_add(struct setting_parser_context *ctx, link = hash_table_lookup(ctx->links, key); if (link != NULL) { if (link->parent == link_copy->parent && - link->info == link_copy->info && - (def == NULL || def->type == SET_DEFLIST_UNIQUE)) + link->info == link_copy->info) return 0; settings_parser_set_error(ctx, t_strconcat(key, " already exists", NULL)); @@ -406,43 +302,30 @@ setting_link_add(struct setting_parser_context *ctx, link->full_key = key; i_assert(hash_table_lookup(ctx->links, key) == NULL); hash_table_insert(ctx->links, key, link); - - if (link->info->struct_size != 0) - setting_link_init_set_struct(ctx, link); return 0; } static int ATTR_NULL(3, 8) -get_deflist(struct setting_parser_context *ctx, struct setting_link *parent, - const struct setting_define *def, - const struct setting_parser_info *info, - const char *key, const char *value, ARRAY_TYPE(void_array) *result, - ARRAY_TYPE(void_array) *change_result) +get_strlist(struct setting_parser_context *ctx, struct setting_link *parent, + const char *key, const char *value, ARRAY_TYPE(void_array) *result) { struct setting_link new_link; const char *const *list; char *full_key; - i_assert(info->defines != NULL || info == &strlist_info); - if (!array_is_created(result)) p_array_init(result, ctx->set_pool, 5); - if (change_result != NULL && !array_is_created(change_result)) - p_array_init(change_result, ctx->set_pool, 5); i_zero(&new_link); new_link.parent = parent; - new_link.info = info; + new_link.info = &strlist_info; new_link.array = result; - new_link.change_array = change_result; - if (info == &strlist_info) { - /* there are no sections below strlist, so allow referencing it - without the key (e.g. plugin/foo instead of plugin/0/foo) */ - full_key = p_strdup(ctx->parser_pool, key); - if (setting_link_add(ctx, def, &new_link, full_key) < 0) - return -1; - } + /* there are no sections below strlist, so allow referencing it + without the key (e.g. plugin/foo instead of plugin/0/foo) */ + full_key = p_strdup(ctx->parser_pool, key); + if (setting_link_add(ctx, &new_link, full_key) < 0) + return -1; list = t_strsplit(value, ",\t "); for (; *list != NULL; list++) { @@ -451,7 +334,7 @@ get_deflist(struct setting_parser_context *ctx, struct setting_link *parent, full_key = p_strconcat(ctx->parser_pool, key, SETTINGS_SEPARATOR_S, *list, NULL); - if (setting_link_add(ctx, def, &new_link, full_key) < 0) + if (setting_link_add(ctx, &new_link, full_key) < 0) return -1; } return 0; @@ -485,9 +368,6 @@ settings_parse(struct setting_parser_context *ctx, struct setting_link *link, ctx->prev_info = link->info; - if (link->set_struct == NULL) - setting_link_init_set_struct(ctx, link); - change_ptr = link->change_struct == NULL ? NULL : STRUCT_MEMBER_P(link->change_struct, def->offset); @@ -547,16 +427,10 @@ settings_parse(struct setting_parser_context *ctx, struct setting_link *link, *(const char *const *)ptr2) < 0) return -1; break; - case SET_DEFLIST: - case SET_DEFLIST_UNIQUE: - ctx->prev_info = def->list_info; - return get_deflist(ctx, link, def, def->list_info, - key, value, (ARRAY_TYPE(void_array) *)ptr, - (ARRAY_TYPE(void_array) *)change_ptr); case SET_STRLIST: { ctx->prev_info = &strlist_info; - if (get_deflist(ctx, link, NULL, &strlist_info, key, value, - (ARRAY_TYPE(void_array) *)ptr, NULL) < 0) + if (get_strlist(ctx, link, key, value, + (ARRAY_TYPE(void_array) *)ptr) < 0) return -1; break; } @@ -653,13 +527,9 @@ settings_find_key_nth(struct setting_parser_context *ctx, const char *key, } *link_r = link; - if (link->info == &strlist_info) { - *def_r = NULL; - return TRUE; - } else { - *def_r = setting_define_find(link->info, end + 1); - return *def_r != NULL; - } + i_assert(link->info == &strlist_info); + *def_r = NULL; + return TRUE; } static bool @@ -851,10 +721,6 @@ settings_parse_get_prev_info(struct setting_parser_context *ctx) bool settings_check(struct event *event, const struct setting_parser_info *info, pool_t pool, void *set, const char **error_r) { - const struct setting_define *def; - const ARRAY_TYPE(void_array) *val; - void *const *children; - unsigned int i, count; bool valid; if (info->check_func != NULL) { @@ -871,22 +737,6 @@ bool settings_check(struct event *event, const struct setting_parser_info *info, if (!valid) return FALSE; } - - for (def = info->defines; def->key != NULL; def++) { - if (!SETTING_TYPE_IS_DEFLIST(def->type)) - continue; - - val = CONST_PTR_OFFSET(set, def->offset); - if (!array_is_created(val)) - continue; - - children = array_get(val, &count); - for (i = 0; i < count; i++) { - if (!settings_check(event, def->list_info, pool, - children[i], error_r)) - return FALSE; - } - } return TRUE; } @@ -912,9 +762,8 @@ settings_var_expand_info(const struct setting_parser_info *info, void *set, const char **error_r) { const struct setting_define *def; - void *value, *const *children; + void *value; const char *error; - unsigned int i, count; int ret, final_ret = 1; for (def = info->defines; def->key != NULL; def++) { @@ -961,25 +810,6 @@ settings_var_expand_info(const struct setting_parser_info *info, void *set, } break; } - case SET_DEFLIST: - case SET_DEFLIST_UNIQUE: { - const ARRAY_TYPE(void_array) *val = value; - - if (!array_is_created(val)) - break; - - children = array_get(val, &count); - for (i = 0; i < count; i++) { - ret = settings_var_expand_info(def->list_info, - children[i], pool, table, func_table, - func_context, str, &error); - if (final_ret > ret) { - final_ret = ret; - *error_r = error; - } - } - break; - } } } @@ -1034,19 +864,7 @@ void settings_var_skip(const struct setting_parser_info *info, void *set) &error); } -static void settings_set_parent(const struct setting_parser_info *info, - void *child, void *parent) -{ - void **ptr; - - if (info->parent_offset1 == 0) - return; - - ptr = PTR_OFFSET(child, info->parent_offset1-1); - *ptr = parent; -} - -static bool +static void setting_copy(enum setting_type type, const void *src, void *dest, pool_t pool, bool keep_values) { @@ -1094,9 +912,6 @@ setting_copy(enum setting_type type, const void *src, void *dest, pool_t pool, *dest_str = p_strdup(pool, *src_str); break; } - case SET_DEFLIST: - case SET_DEFLIST_UNIQUE: - return FALSE; case SET_STRLIST: { const ARRAY_TYPE(const_string) *src_arr = src; ARRAY_TYPE(const_string) *dest_arr = dest; @@ -1161,7 +976,6 @@ setting_copy(enum setting_type type, const void *src, void *dest, pool_t pool, case SET_ALIAS: break; } - return TRUE; } static void *settings_dup_full(const struct setting_parser_info *info, @@ -1169,8 +983,7 @@ static void *settings_dup_full(const struct setting_parser_info *info, { const struct setting_define *def; const void *src; - void *dest_set, *dest, *const *children; - unsigned int i, count; + void *dest_set, *dest; if (info->struct_size == 0) return NULL; @@ -1182,25 +995,7 @@ static void *settings_dup_full(const struct setting_parser_info *info, src = CONST_PTR_OFFSET(set, def->offset); dest = PTR_OFFSET(dest_set, def->offset); - if (!setting_copy(def->type, src, dest, pool, keep_values)) { - const ARRAY_TYPE(void_array) *src_arr = src; - ARRAY_TYPE(void_array) *dest_arr = dest; - void *child_set; - - if (!array_is_created(src_arr)) - continue; - - children = array_get(src_arr, &count); - p_array_init(dest_arr, pool, count); - for (i = 0; i < count; i++) { - child_set = settings_dup_full(def->list_info, - children[i], pool, - keep_values); - array_push_back(dest_arr, &child_set); - settings_set_parent(def->list_info, child_set, - dest_set); - } - } + setting_copy(def->type, src, dest, pool, keep_values); } if (info->pool_offset1 > 0) { @@ -1228,8 +1023,7 @@ settings_changes_dup(const struct setting_parser_info *info, { const struct setting_define *def; const void *src; - void *dest_set, *dest, *const *children; - unsigned int i, count; + void *dest_set, *dest; if (change_set == NULL || info->struct_size == 0) return NULL; @@ -1254,25 +1048,6 @@ settings_changes_dup(const struct setting_parser_info *info, case SET_FILTER_ARRAY: *((uint8_t *)dest) = *((const uint8_t *)src); break; - case SET_DEFLIST: - case SET_DEFLIST_UNIQUE: { - const ARRAY_TYPE(void_array) *src_arr = src; - ARRAY_TYPE(void_array) *dest_arr = dest; - void *child_set; - - if (!array_is_created(src_arr)) - break; - - children = array_get(src_arr, &count); - p_array_init(dest_arr, pool, count); - for (i = 0; i < count; i++) { - child_set = settings_changes_dup(def->list_info, - children[i], - pool); - array_push_back(dest_arr, &child_set); - } - break; - } case SET_FILTER_NAME: case SET_ALIAS: break; @@ -1386,208 +1161,6 @@ settings_parser_dup(const struct setting_parser_context *old_ctx, return new_ctx; } -static void * -settings_changes_init(const struct setting_parser_info *info, - const void *change_set, pool_t pool) -{ - const struct setting_define *def; - const ARRAY_TYPE(void_array) *src_arr; - ARRAY_TYPE(void_array) *dest_arr; - void *dest_set, *set, *const *children; - unsigned int i, count; - - if (info->struct_size == 0) - return NULL; - - dest_set = p_malloc(pool, info->struct_size); - for (def = info->defines; def->key != NULL; def++) { - if (!SETTING_TYPE_IS_DEFLIST(def->type)) - continue; - - src_arr = CONST_PTR_OFFSET(change_set, def->offset); - dest_arr = PTR_OFFSET(dest_set, def->offset); - - if (array_is_created(src_arr)) { - children = array_get(src_arr, &count); - i_assert(!array_is_created(dest_arr)); - p_array_init(dest_arr, pool, count); - for (i = 0; i < count; i++) { - set = settings_changes_init(def->list_info, - children[i], pool); - array_push_back(dest_arr, &set); - } - } - } - return dest_set; -} - -static void settings_copy_deflist(const struct setting_define *def, - const struct setting_link *src_link, - struct setting_link *dest_link, - pool_t pool) -{ - const ARRAY_TYPE(void_array) *src_arr; - ARRAY_TYPE(void_array) *dest_arr; - void *const *children, *child_set; - unsigned int i, count; - - src_arr = CONST_PTR_OFFSET(src_link->set_struct, def->offset); - dest_arr = PTR_OFFSET(dest_link->set_struct, def->offset); - - if (!array_is_created(src_arr)) - return; - - children = array_get(src_arr, &count); - if (!array_is_created(dest_arr)) - p_array_init(dest_arr, pool, count); - for (i = 0; i < count; i++) { - child_set = settings_dup(def->list_info, children[i], pool); - array_push_back(dest_arr, &child_set); - settings_set_parent(def->list_info, child_set, - dest_link->set_struct); - } - - /* copy changes */ - dest_arr = PTR_OFFSET(dest_link->change_struct, def->offset); - if (!array_is_created(dest_arr)) - p_array_init(dest_arr, pool, count); - for (i = 0; i < count; i++) { - child_set = settings_changes_init(def->list_info, - children[i], pool); - array_push_back(dest_arr, &child_set); - } -} - -static int -settings_copy_deflist_unique(const struct setting_define *def, - const struct setting_link *src_link, - struct setting_link *dest_link, - pool_t pool, const char **conflict_key_r) -{ - struct setting_link child_dest_link, child_src_link; - const ARRAY_TYPE(void_array) *src_arr, *src_carr; - ARRAY_TYPE(void_array) *dest_arr, *dest_carr; - void *const *src_children, *const *src_cchildren; - void *const *dest_children, *const *dest_cchildren, *child_set; - const char *const *src_namep, *const *dest_namep; - unsigned int i, j, src_count, dest_count, ccount; - unsigned int type_offset; - - i_assert(def->list_info->type_offset1 != 0); - - src_arr = CONST_PTR_OFFSET(src_link->set_struct, def->offset); - src_carr = CONST_PTR_OFFSET(src_link->change_struct, def->offset); - dest_arr = PTR_OFFSET(dest_link->set_struct, def->offset); - dest_carr = PTR_OFFSET(dest_link->change_struct, def->offset); - - if (!array_is_created(src_arr)) - return 0; - type_offset = def->list_info->type_offset1-1; - - i_zero(&child_dest_link); - i_zero(&child_src_link); - - child_dest_link.info = child_src_link.info = def->list_info; - - src_children = array_get(src_arr, &src_count); - src_cchildren = array_get(src_carr, &ccount); - i_assert(src_count == ccount); - if (!array_is_created(dest_arr)) { - p_array_init(dest_arr, pool, src_count); - p_array_init(dest_carr, pool, src_count); - } - for (i = 0; i < src_count; i++) { - src_namep = CONST_PTR_OFFSET(src_children[i], type_offset); - dest_children = array_get(dest_arr, &dest_count); - dest_cchildren = array_get(dest_carr, &ccount); - i_assert(dest_count == ccount); - for (j = 0; j < dest_count; j++) { - dest_namep = CONST_PTR_OFFSET(dest_children[j], - type_offset); - if (strcmp(*src_namep, *dest_namep) == 0) - break; - } - - if (j < dest_count && **src_namep != '\0') { - /* merge */ - child_src_link.set_struct = src_children[i]; - child_src_link.change_struct = src_cchildren[i]; - child_dest_link.set_struct = dest_children[j]; - child_dest_link.change_struct = dest_cchildren[j]; - if (settings_apply(&child_dest_link, &child_src_link, - pool, conflict_key_r) < 0) - return -1; - } else { - /* append */ - child_set = settings_dup(def->list_info, - src_children[i], pool); - array_push_back(dest_arr, &child_set); - settings_set_parent(def->list_info, child_set, - dest_link->set_struct); - - child_set = settings_changes_init(def->list_info, - src_cchildren[i], - pool); - array_push_back(dest_carr, &child_set); - } - } - return 0; -} - -static int -settings_apply(struct setting_link *dest_link, - const struct setting_link *src_link, - pool_t pool, const char **conflict_key_r) -{ - const struct setting_define *def; - const void *src, *csrc; - void *dest, *cdest; - - for (def = dest_link->info->defines; def->key != NULL; def++) { - csrc = CONST_PTR_OFFSET(src_link->change_struct, def->offset); - cdest = PTR_OFFSET(dest_link->change_struct, def->offset); - - if (def->type == SET_DEFLIST || def->type == SET_STRLIST || - def->type == SET_FILTER_ARRAY) { - /* just add the new values */ - } else if (def->type == SET_DEFLIST_UNIQUE) { - /* merge sections */ - } else if (*((const uint8_t *)csrc) == 0) { - /* unchanged */ - continue; - } else if (def->type == SET_ALIAS) { - /* ignore aliases */ - continue; - } else if (*((const uint8_t *)cdest) != 0) { - /* conflict */ - if (conflict_key_r != NULL) { - *conflict_key_r = def->key; - return -1; - } - continue; - } else { - *((uint8_t *)cdest) = *(const uint8_t *)csrc; - } - - /* found a changed setting */ - src = CONST_PTR_OFFSET(src_link->set_struct, def->offset); - dest = PTR_OFFSET(dest_link->set_struct, def->offset); - - if (setting_copy(def->type, src, dest, pool, FALSE)) { - /* non-list */ - } else if (def->type == SET_DEFLIST) { - settings_copy_deflist(def, src_link, dest_link, pool); - } else { - i_assert(def->type == SET_DEFLIST_UNIQUE); - if (settings_copy_deflist_unique(def, src_link, - dest_link, pool, - conflict_key_r) < 0) - return -1; - } - } - return 0; -} - const char *settings_section_escape(const char *name) { #define CHAR_NEED_ESCAPE(c) \ diff --git a/src/lib-settings/settings-parser.h b/src/lib-settings/settings-parser.h index ffa56f1d3a..022e6f6446 100644 --- a/src/lib-settings/settings-parser.h +++ b/src/lib-settings/settings-parser.h @@ -27,8 +27,6 @@ enum setting_type { SET_STR, SET_STR_VARS, /* string with %variables */ SET_ENUM, - SET_DEFLIST, /* of type array_t */ - SET_DEFLIST_UNIQUE, SET_STRLIST, /* of type ARRAY_TYPE(const_string) */ SET_ALIAS, /* alias name for above setting definition */ SET_FILTER_NAME, @@ -37,10 +35,8 @@ enum setting_type { enum setting_flags { SET_FLAG_HIDDEN = BIT(0), }; -#define SETTING_TYPE_IS_DEFLIST(type) \ - ((type) == SET_DEFLIST || (type) == SET_DEFLIST_UNIQUE) -#define SETTING_DEFINE_LIST_END { 0, 0, NULL, 0, NULL, NULL, NULL } +#define SETTING_DEFINE_LIST_END { 0, 0, NULL, 0, NULL, NULL } struct setting_define { enum setting_type type; @@ -48,7 +44,6 @@ struct setting_define { const char *key; size_t offset; - const struct setting_parser_info *list_info; const char *filter_array_field_name; const char *required_setting; }; @@ -118,9 +113,6 @@ struct setting_parser_info { size_t type_offset1; /* type_offset+1. 0=nonexistent. */ size_t struct_size; - size_t parent_offset1; /* parent_offset+1. 0=nonexistent. */ - const struct setting_parser_info *parent; - size_t pool_offset1; /* pool_offset+1. 0=nonexistent. */ bool (*check_func)(void *set, pool_t pool, const char **error_r);