From: Timo Sirainen Date: Mon, 26 Dec 2022 20:21:43 +0000 (-0500) Subject: lib-master, config: Support disabling settings checks X-Git-Tag: 2.4.0~3051 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=57312572ae64e295c91baba24ec65a961d44dbbf;p=thirdparty%2Fdovecot%2Fcore.git lib-master, config: Support disabling settings checks This is intended for managesieve's dump-capability. --- diff --git a/src/config/config-connection.c b/src/config/config-connection.c index d23884a861..6533eba3fd 100644 --- a/src/config/config-connection.c +++ b/src/config/config-connection.c @@ -53,22 +53,31 @@ static int config_connection_request(struct config_connection *conn, const char *const *args ATTR_UNUSED) { const char *import_environment; - - if (null_strcmp(*args, "reload") == 0) { - const char *path, *error; - - path = master_service_get_config_path(master_service); - if (config_parse_file(path, CONFIG_PARSE_FLAG_EXPAND_VALUES, &error) <= 0) { - o_stream_nsend_str(conn->output, - t_strconcat("-", error, "\n", NULL)); + enum config_dump_flags flags = CONFIG_DUMP_FLAG_CHECK_SETTINGS; + + while (*args != NULL) { + if (strcmp(*args, "disable-check-settings") == 0) + flags &= ENUM_NEGATE(CONFIG_DUMP_FLAG_CHECK_SETTINGS); + else if (strcmp(*args, "reload") == 0) { + const char *path, *error; + + path = master_service_get_config_path(master_service); + if (config_parse_file(path, CONFIG_PARSE_FLAG_EXPAND_VALUES, &error) <= 0) { + o_stream_nsend_str(conn->output, + t_strconcat("-", error, "\n", NULL)); + return 0; + } + i_close_fd(&global_config_fd); + } else { + o_stream_nsend_str(conn->output, "-Unknown parameters\n"); return 0; } - i_close_fd(&global_config_fd); + args++; } if (global_config_fd == -1) { int fd = config_dump_full(CONFIG_DUMP_FULL_DEST_RUNDIR, - &import_environment); + flags, &import_environment); if (fd == -1) { o_stream_nsend_str(conn->output, "-Failed\n"); return 0; diff --git a/src/config/config-dump-full.c b/src/config/config-dump-full.c index a627cb5e46..92869f26f0 100644 --- a/src/config/config-dump-full.c +++ b/src/config/config-dump-full.c @@ -148,6 +148,7 @@ config_dump_full_sections(struct ostream *output, } int config_dump_full(enum config_dump_full_dest dest, + enum config_dump_flags flags, const char **import_environment_r) { struct config_export_context *export_ctx; @@ -162,11 +163,11 @@ int config_dump_full(enum config_dump_full_dest dest, if (dest == CONFIG_DUMP_FULL_DEST_STDOUT) { export_ctx = config_export_init( - CONFIG_DUMP_SCOPE_CHANGED, 0, + CONFIG_DUMP_SCOPE_CHANGED, flags, config_dump_full_stdout_callback, &dump_ctx); } else { export_ctx = config_export_init( - CONFIG_DUMP_SCOPE_CHANGED, 0, + CONFIG_DUMP_SCOPE_CHANGED, flags, config_dump_full_callback, &dump_ctx); } i_zero(&empty_filter); diff --git a/src/config/config-dump-full.h b/src/config/config-dump-full.h index 56a364a3e3..a7a5090437 100644 --- a/src/config/config-dump-full.h +++ b/src/config/config-dump-full.h @@ -1,6 +1,8 @@ #ifndef CONFIG_DUMP_FULL #define CONFIG_DUMP_FULL +#include "config-request.h" + enum config_dump_full_dest { CONFIG_DUMP_FULL_DEST_RUNDIR, CONFIG_DUMP_FULL_DEST_TEMPDIR, @@ -8,6 +10,7 @@ enum config_dump_full_dest { }; int config_dump_full(enum config_dump_full_dest dest, + enum config_dump_flags flags, const char **import_environment_r); #endif diff --git a/src/config/config-parser.c b/src/config/config-parser.c index 47bfff3428..dc0ac0977b 100644 --- a/src/config/config-parser.c +++ b/src/config/config-parser.c @@ -998,7 +998,8 @@ int config_parse_file(const char *path, enum config_parse_flags flags, i_zero(&ctx); ctx.pool = pool_alloconly_create(MEMPOOL_GROWING"config file parser", 1024*256); ctx.path = path; - ctx.hide_errors = fd == -1; + ctx.hide_errors = fd == -1 || + (flags & CONFIG_PARSE_FLAG_HIDE_ERRORS) != 0; for (count = 0; all_roots[count] != NULL; count++) ; ctx.root_parsers = diff --git a/src/config/config-parser.h b/src/config/config-parser.h index 5d11adaf44..819c65fce2 100644 --- a/src/config/config-parser.h +++ b/src/config/config-parser.h @@ -7,6 +7,7 @@ enum config_parse_flags { CONFIG_PARSE_FLAG_EXPAND_VALUES = BIT(0), + CONFIG_PARSE_FLAG_HIDE_ERRORS = BIT(1), }; struct config_module_parser { diff --git a/src/config/doveconf.c b/src/config/doveconf.c index 182c4212c5..6d78bd2e10 100644 --- a/src/config/doveconf.c +++ b/src/config/doveconf.c @@ -867,6 +867,7 @@ int main(int argc, char *argv[]) bool simple_output = FALSE; bool dump_defaults = FALSE, host_verify = FALSE, dump_full = FALSE; bool print_plugin_banner = FALSE, hide_passwords = TRUE; + bool disable_check_settings = FALSE; if (getenv("USE_SYSEXITS") != NULL) { /* we're coming from (e.g.) LDA */ @@ -875,7 +876,7 @@ int main(int argc, char *argv[]) i_zero(&filter); master_service = master_service_init("config", master_service_flags, - &argc, &argv, "adf:FhHm:nNpPexsS"); + &argc, &argv, "adEf:FhHm:nNpPexsS"); orig_config_path = t_strdup(master_service_get_config_path(master_service)); i_set_failure_prefix("doveconf: "); @@ -886,6 +887,9 @@ int main(int argc, char *argv[]) case 'd': dump_defaults = TRUE; break; + case 'E': + disable_check_settings = TRUE; + break; case 'f': filter_parse_arg(&filter, optarg); break; @@ -968,6 +972,8 @@ int main(int argc, char *argv[]) enum config_parse_flags flags = 0; if (expand_vars) flags |= CONFIG_PARSE_FLAG_EXPAND_VALUES; + if (disable_check_settings) + flags |= CONFIG_PARSE_FLAG_HIDE_ERRORS; if ((ret = config_parse_file(dump_defaults ? NULL : config_path, flags, &error)) == 0 && access(EXAMPLE_CONFIG_DIR, X_OK) == 0) { @@ -978,11 +984,15 @@ int main(int argc, char *argv[]) if ((ret == -1 && exec_args != NULL) || ret == 0 || ret == -2) i_fatal("%s", error); + enum config_dump_flags dump_flags = disable_check_settings ? 0 : + CONFIG_DUMP_FLAG_CHECK_SETTINGS; if (dump_full && exec_args == NULL) { ret2 = config_dump_full(CONFIG_DUMP_FULL_DEST_STDOUT, + dump_flags, &import_environment); } else if (dump_full) { int temp_fd = config_dump_full(CONFIG_DUMP_FULL_DEST_TEMPDIR, + dump_flags, &import_environment); if (getenv(DOVECOT_PRESERVE_ENVS_ENV) != NULL) { /* Standalone binary is getting its configuration via diff --git a/src/lib-master/master-service-settings.c b/src/lib-master/master-service-settings.c index 45354dcbcd..e8ea4f6879 100644 --- a/src/lib-master/master-service-settings.c +++ b/src/lib-master/master-service-settings.c @@ -7,6 +7,7 @@ #include "mmap-util.h" #include "fdpass.h" #include "write-full.h" +#include "str.h" #include "syslog-util.h" #include "eacces-error.h" #include "env-util.h" @@ -212,6 +213,8 @@ master_service_exec_config(struct master_service *service, strarr_push(&conf_argv, "-c"); strarr_push(&conf_argv, service->config_path); + if (input->disable_check_settings) + strarr_push(&conf_argv, "-E"); strarr_push(&conf_argv, "-F"); strarr_push(&conf_argv, binary_path); array_append(&conf_argv, (const char *const *)service->argv + 1, @@ -319,11 +322,15 @@ master_service_open_config(struct master_service *service, } } net_set_nonblock(fd, FALSE); - const char *str = !input->reload_config ? - CONFIG_HANDSHAKE"REQ\n" : - CONFIG_HANDSHAKE"REQ\treload\n"; + string_t *str = t_str_new(128); + str_append(str, CONFIG_HANDSHAKE"REQ"); + if (input->reload_config) + str_append(str, "\treload"); + if (input->disable_check_settings) + str_append(str, "\tdisable-check-settings"); + str_append_c(str, '\n'); alarm(CONFIG_READ_TIMEOUT_SECS); - int ret = write_full(fd, str, strlen(str)); + int ret = write_full(fd, str_data(str), str_len(str)); if (ret < 0) *error_r = t_strdup_printf("write_full(%s) failed: %m", path); @@ -650,10 +657,12 @@ int master_service_settings_read(struct master_service *service, } } - if (!settings_parser_check(parser, service->set_pool, &error)) { - *error_r = t_strdup_printf("Invalid settings: %s", error); - settings_parser_unref(&parser); - return -1; + if (!input->disable_check_settings) { + if (!settings_parser_check(parser, service->set_pool, &error)) { + *error_r = t_strdup_printf("Invalid settings: %s", error); + settings_parser_unref(&parser); + return -1; + } } service->set = settings_parser_get_root_set(parser, diff --git a/src/lib-master/master-service-settings.h b/src/lib-master/master-service-settings.h index 867c55d3cc..15eb84ce96 100644 --- a/src/lib-master/master-service-settings.h +++ b/src/lib-master/master-service-settings.h @@ -43,6 +43,7 @@ struct master_service_settings_input { bool always_exec; bool return_config_fd; bool use_sysexits; + bool disable_check_settings; const char *service; const char *username;